For a function of several variables, one can calculate its derivative in a certain direction. In particular, the directional derivatives in coordinate directions are called partial derivatives. All partial derivatives of the function form a vector called **gradient** of the function . Gradient of a (scalar) function of variables is a vector-valued function of variables.

With gradient notation, one can write the **linear approximation** of around (first-order Taylor expansion) as

$$ f(x) = f(\mathbf{x}_0) + \nabla f(\mathbf{x}_0) (\mathbf{x} – \mathbf{x}_0) + O(|\mathbf{x} – \mathbf{x}_0|^2).$$

Note that the linear part of the expansion $$ g(x) = f(\mathbf{x}_0) + \nabla f(\mathbf{x}_0) (\mathbf{x} – \mathbf{x}_0) $$ is a function whose graph being the **tangent plane** of the graph of at .

In addition, when given an **equation** , with , it defines a relation among components of . Whenever , the equation fixes the value of $x_i$ as an implicit function locally around (**inverse function theorem**).

Geometrically, the equation defines a surface in . The tangent plane of such a surface can be also given by manipulating the gradient of the function:

$$ 0 = \nabla f(\mathbf{x}_0) (\mathbf{x} – \mathbf{x}_0). $$

Note that here is a point on the surface, i.e., .

As with functions of single variable, to solve problems of the form

$$ \max _{\mathbf{x} \in D, D \subset \mathbb{R}^n} f(\mathbf{x}) \text{ or } \min _{\mathbf{x} \in D, D \subset \mathbb{R}^n} f(\mathbf{x}), $$

one needs to divide the problem into sub-problems by investigating

- Critical points of which solves .
- Points on .

Unlike functions of a single variable, critical points of a function of several variables may be local maxima, local minima, or saddle point, depending on eigenvalues of the Hessian matrix. When the Hessian matrix is non-degenerate, a critical point is a

- Local minima, if all eigenvalues are non-negative.
- Local maxima, if all eigenvalues are non-positive.
- Saddle point, if eigenvalues are of mixed signs.

Single integration calculates the enclosed area of the graph of the function within interval . Likewise, double integration calculate the enclose volume of the graph of the function within region . Similar concept of “**volume**” can be generalized to arbitrary dimension, yielding analogous multiple integration , where .

To actually calculate the value of multiple integrations, it is usually convenient to convert them to **iterated integrals**, which can be then calculated iteratively using the fundamental theorem of calculus. This process is justified by Fubini’s theorem

Vector fields are functions that map a position in space to a direction ().

A vector field is called a **gradient field** (also called **conservative field**) if there exists a potential function for such that

$$ \mathbf{F} = \nabla \phi. $$

Force fields in physics can be modeled using vector fields. When a particle travels through space along a curve subject to the force field, the work done throughout the process is given by

$$ W = \int_C \mathbf{F}(\mathbf{r}(s)) \cdot d \mathbf{r}(s) = \int_C \mathbf{F}(\mathbf{r}(s)) \cdot \mathbf{r}'(s) ds.$$

This is a scalar integration that can be calculated directly.

Specially, when is conservative,

$$ \mathbf{F}(\mathbf{r}(s)) \cdot d \mathbf{r}(s) = \nabla \phi (\mathbf{r}(s)) \cdot d \mathbf{r}(s) = d \phi (\mathbf{r}(s)). $$

That is, given a conservative force field, the work is equal to

$$ W = \int_C d \phi (\mathbf{r}(s)) = \phi(\mathbf{x}_e) – \phi(\mathbf{x}_s), $$

which only depends on the starting point and the ending point (and independent of the path).

Linux is known for its stability and reliability. Personally, I never rebooted my Linux machine until recently I realized that it is still running an old kernel version despite its being upgraded multiple times. To load the newer kernel, I had to reboot the machine.

Frankly speaking, the old kernel runs just fine. The only reason to reboot is to load a newer kernel. Sometimes it might matter, for example when there are security updates. To find out whether a reboot is needed, you can check for the versions of the running kernel and the kernel installed on the hard drive.

$ uname -r # version of running kernel 4.10.13-1-ARCH $ file /boot/vmlinuz-linux # kernel on the hard drive /boot/vmlinuz-linux: Linux kernel x86 boot executable bzImage, version 4.10.13-1-ARCH (builduser@tobias) #1 SMP PREEMPT Thu Apr 27 12:15:09 CEST 2017, RO-rootFS, swap_dev 0x4, Normal VGA

If the output of the two commands shows different versions, a reboot is suggested.

]]>

Launch VirtualBox, create a new machine and install the system of your choice, which depends largely on your personal preferences. For me, I have been using Arch Linux for a while and is happy about it. Instead of manually setting up everything, I used Arch-Anywhere to install Arch Linux with Openbox.

There are other Archer installers out there, like AUI, Revenge, etc. All of them should do the job well, I chose Arch-Anywhere mainly due to its simplicity.

After guest system installation, we have a fresh installed Arch Linux machine. Now it’s time to do some basic setup.

Before start, it is advised that `virtualbox-guest-utils`

be installed to have more support of virtualbox features. After that, enable `vboxservice.service`

to load the modules and synchronize the guest’s system time with the host. Also, add `VBoxClient-all`

to autostart script on login to support (see this entry on Arch Wiki):

- shared clipboard and drag and drop between the host and the guest;
- seamless window mode;
- the guest display is automatically resized according to the size of the guest window;
- checking the VirtualBox host version.

sudo pacman -S virtualbox-guest-utils sudo systemctl enable vboxservice.service

Also, I would like to bring some configurations over from a physical machine I have been using to this virtual machine.

It is easy using `pacman`

to export the list of all packages (explicitly) installed on the old machine and install them on the new one.

# On the old machine sudo pacman -Qe | awk '{print $1}' > packages.txt # Copy packages.txt to the new virtual machine and do for x in $(cat package_list.txt); do pacman -S $x; done # Or sudo pacman -S `cat package_list.txt` #This will also work, but Pacman will exit if you have a package #installed that is not in the repositories.

I am managing many of my configuration files in this Github repo. Using it is as simple as cloning it somewhere and run `./install.sh`

.

git clone git@github.com:xywei/dot-files.git cd dot-files ./install.sh

Since I would like to connect to the guest machine via ssh, `sshd.service`

should be enabled. Also remember to double check on `/etc/ssh/sshd_config`

.

sudo pacman -S openssh sudo systemctl enable sshd.service

Some setup is also needed on the host side to make things perform smoothly.

Shared folders can be easily setup using VirtualBox GUI. Check the auto-mount option and you don’t have to worry about mounting them on the guest side. Just to make sure that the user of the guest machine is under `vboxsf`

group to have the right access to those shared folders.

By default, the shared folders are mounted under `/media/sf_FolderName`

.

To access the guest machine using `ssh`

, you need to:

- Create the
`vboxnet0`

interface. Using VirtualBox GUI, go to VirtualBox > File > Preferences > Network > Host-only Networks > Add. - Shutdown the virtual machine and enable I/O APIC. VM’s Settings > System > check “Enable I/O APIC.”
- Add adapter for
`vboxnet0`

. VM’s Settings > Network > Adapter 2 > host-only vboxnet0. - Configuring port forwarding with NAT. VM’s Settings > Network > Adapter 1 (Attached to NAT) > Advanced > Port Forwarding. Add a new rule with each column “GuestSSH,tcp, ,2222, ,22”.

Now, you should be able to start the virtual machine and connect to it via `ssh`

ssh -l -p 2222 localhost

Now that the virtual machine is ready for use, here is my preferred way of using it.

I prefer to use the virtual machine via `ssh`

. Using VirtualBox CLI, we can start the machine using the following command:

VBoxManage startvm MachineName --type=headless

To shutdown the machine, use

VBoxManage controlvm MachineName poweroff soft]]>

ParaView-Superbuild is a project to build ParaView and its dependencies.

To use it, we need:

- A CXX11 compiler (can be installed using Spack).
- CMake (can also installed using Spack).
- MPI (instead of using system’s MPI, I used openmpi installed using Spack. It is unclear what are the side effects).

After setting up these dependencies, clone the project with submodules:

git clone --recursive https://gitlab.kitware.com/paraview/paraview-superbuild.git

Then, checkout a specific tag from the superbuild git repository:

git checkout v5.2.0 && git submodule update

Next, create a build directory OUTSIDE of the clone.

cd .. && mkdir -p superbuild-build && cd superbuild-build

Revoke CMake from within the build direcotory

cmake -DCMAKE_INSTALL_PREFIX=/path/to/install/paraview \ -DCMAKE_C_COMPILER=/path/to/c/compiler \ -DCMAKE_CXX_COMPILER=/path/to/cxx/compiler \ -DENABLE_mpi=ON -DUSE_SYSTEM_mpi=ON \ -DENABLE_tbb=ON -DUSE_SYSTEM_tbb=OFF \ -DSUPERBUILD_DEFAULT_INSTALL=paraview/DragNDrop \ ../paraview-superbuild

A few notes on the arguments:

- SUPERBUILD_DEFAULT_INSTALL=paraview/DragNDrop. This is required, otherwise superbuild will try to install dependencies into /usr/local/.
- CMAKE_INSTALL_PREFIX is the install directory for paraview.
- CMAKE_C_COMPILER and CMAKE_CXX_COMPILER are set to be the ones that support CXX11.
- ENABLE_mpi=ON to enable MPI support. This is the whole point of deploying Paraview on a cluster.
- DUSE_SYSTEM_mpi=ON to pick up system MPI.

Lastly,

make && make install

and chill.

**Remark:** Things can go wrong with polluted environment variables. In that case, add these lines to the top of `~/.bashrc`

(before setting up Spack):

unset LIBRARY_PATH unset LD_LIBRARY_PATH unset DYLD_LIBRARY_PATH unset CPATH unset TBB22_INSTALL_DIR]]>

WeBWork is an open-source online homework system built using Java, which is definitely not the most secure way to run a web application. (Read more: Why are Java’s Vulnerabilities One of the Biggest Security Holes on Your Computer?).

Luckily, most of the time the user can get along without running Java; however, sometimes problems can happen, involving interactive images that cannot be displayed normally without Java enabled.

There is another way to have the similar thing without risking having Java. The process consists of two steps: First, find the function expression you have, and second visualize that function with proper tools.

For example, the following image shows a problem where the image cannot be displayed.

To find the exact function expression you are dealing with, it needs a little understanding of how the system works. The problem you actually see is a result of combining a predefined prototype with several randomly generated parameters. Those parameters can be found in the page source within

tag like this:

While the prototype may need some search on the Internet. Usually, it can be found in some open source repositories. Here, the value of “INPUT_FILE” hints us to search for “trace-5b”, leading to the problem prototype definition hosted on Github.

On line 52 it shows the function to use, and the lines above it show how the parameters are generated.

Now, with all the information ready, you can visualize the function using whatever tool you like. Perhaps the easiest way is to utilize Google search. Like the image shown below.

The plot by Google is interactive, just like what you would expect from the original WeBWork system.

]]>

Denote a parametric curve as . One can calculate the slopes of its tangent lines via chain rule.

Let , . Then for , the slope of its tangent line at the point is:

$$ \frac{dy}{dx} (t_0) = \frac{dy}{dt}(t_0) \left[ \frac{dx}{dt}(t_0) \right] ^{-1} = -\frac{2t_0}{ \sin(t_0) } $$

If the curve is parametrized with the **angle** or **argument** in polar coordinate, i.e.,

$$ r = f(\theta). $$

One can calculate the curve’s enclose area via formula

$$ S = \int_{\theta_1}^{\theta_2} \frac{1}{2} r^2(\theta) d\theta . $$

Let . It encloses a four-petal region. The area of half of a petal is

$$ A = \int_{0}^{\frac{\pi}{4}} \frac{1}{2} (2 \cos 2\theta)^2 d\theta = \frac{\pi}{4}.$$

Thus the area of whole region is .

Here is an animation showing the growth of petals as goes from to .

Denote , as vectors in 2- or 3-dimensional Euclidean space. Then:

- and are
**orthogonal**iff , i.e., the orthogonal projection of one vector on the other has zero norm. - and are
**parallel**iff , i.e., the parallelogram generated by the two vectors has zero area.

More generally, denote as the angle between and , we have:

- Example: Work = Force Displacement.
- Example: Torque = Force Position.

Substitute into the relations above, we have:

Cross product of two vectors is a vector whose direction obeys the right-hand rule. Let , and be the coordinate unit vectors of 3-dimensional Euclidean space. Then conventionally

$$ \mathbf{i} \cdot \mathbf{j} = 0, \quad \mathbf{j} \cdot \mathbf{k} = 0, \quad \mathbf{k} \cdot \mathbf{i} = 0. $$

And

$$ \mathbf{i} \times \mathbf{j} = \mathbf{k}, \quad \mathbf{j} \times \mathbf{k} = \mathbf{i}, \quad \mathbf{k} \times \mathbf{i} = \mathbf{j}. $$

Compute the area of the triangle enclosed by connecting three points: .

The area is $$ \frac{1}{2}|(2,3,4) \times (3,2,0)| = \frac{1}{2} \left| \begin{bmatrix} \mathbf{i} & \mathbf{j}& \mathbf{k} \\ 2 & 3 & 4 \\ 3 & 2 & 0 \end{bmatrix}\right| = \frac{\sqrt{233}}{2}.$$

Now, using the vector notation in 2d, or in 3d, a parametric curve can be written in a unified notation .

Interpreting the parameter as “time”, the curve defines a motion in space; mathematically, it is called a **vector-valued function**. Given any time , this function provides information about the underlying motion:

- : The
**position**in space. - : The
**speed**, (both magnitude and direction). - : The
**acceleration**, (also both magnitude and direction).

The length traveled between two points and along the curve can be calculated by integrating the velocity magnitude along the curve.

A helical path $$ \mathbf{r}(t) = (250 \cos t, 250 \sin t, 100t), \quad t \in [0,10]. $$

The length is $$ S = \int_0^{10} |\mathbf{r}'(t)| dt = \int_0^{10} 269 dt = 2690. $$

Fixing a point on the curve , one can define the arc length function

$$ S(t) = \int_a^{t} |\mathbf{r}'(\tau)| d\tau.$$

By a change of variable, this arc length function can also be used to parametrize the curve

$$ \mathbf{r}(t) = \mathbf{r}( S^{-1}(s) ). $$

In this case, the parameter is called **arc-length parameter**. For lines with equation

$$ \mathbf{r}(t) = \mathbf{u} + t \mathbf{v},$$

this change of variable is simply rescaling to a unit vector, yielding

$$ \mathbf{r}(s) = \mathbf{u} + \frac{s}{|\mathbf{v}|} \mathbf{v},$$

Normally, the motion speed changes in both magnitude and direction; however, with arc-length parametrization, only the direction changes. In this case, the acceleration is directly tied to the curve’s properties:

- Its magnitude is called
**curvature**, which measures the “turn rate” of the curve. - Its direction is called
**principal unit normal vector**, pointing towards the “inside” of the turns.

For general parametrization, the curvature can be calculated using the following formula:

$$ \kappa(t) = \frac{|\mathbf{r}'(t)\times \mathbf{r}”(t)|}{|\mathbf{r}'(t)|^3} $$

A function of variables parametrizes an -dimensional geometric object. For example, a function of one variable parametrizes a curve; similarly, a function of two variables parametrizes a surface .

Alternatively, equations in -dimensional space defines a -dimensional object (co-dimension ). For example, one equation defines a point in 1-dimensional space (“level point”). The same number of equations define a curve in 2-dimensional space (“**level curve**“), and a surface in 3-dimensional space (“level surface”).

Rewrite the plane $$ ax+by+cz + d=0$$ into so-called Hessian normal form $$ \mathbf{\hat{n}} \cdot \mathbf{r} = -p $$ where is the unit normal vector and is the distance of the plane from the origin.

One normal vector is simply , so we can let $$ \mathbf{\hat{n}} = (a/l, b/l, c/l) $$ where . Then $$ p = d/l $$.

**Remark**: The Hessian normal form is especially convenient to calculate point-plane distance: $$ D = \mathbf{\hat{n}} \cdot \mathbf{r} + p $$

The graph of a function is drawn by putting together all its possible input-output pairs (a direct product). For example, drawing the graph of the function is equivalent to drawing the graph of equation , or the zero-level surface of the function .

Typical methods of drawing function graphs by hand:

- Look for symmetry properties, e.g., is the function symmetric with respect to axis?
- Look for intercepts and asymptotes by letting independent variables go to zero or infinity.
- Study its derivatives (to look for monotonicity, convexity).
- Change of coordinate, e.g. changing to polar coordinate may simplify the function and make rotational symmetry properties easier to be seen.
- Plug in numerical values (last resort, always works with sufficient effort).

The notion of limit and continuity for functions of several variables is directly generalized from that of single variable functions, inheriting most of its properties (sum, difference, product, quotient, composite, etc.). One subtle difference, however, is that in 1d, there are only two directions where a point can be approached; but the number is infinite in 2d or higher. A procedure called **two-path test** is thus often used to show the nonexistence of limits.

Show that $$ \lim_{(x,y)\longrightarrow (0,0)} \frac{(x+y)^2}{x^2+y^2}$$ does not exist.

Let along a straight line with constant slope , i.e., . Then $$ \lim_{(x,mx)\longrightarrow (0,0)} \frac{(x+mx)^2}{x^2+(mx)^2} = \frac{(1+m)^2}{1+m^2}$$ which depends on the direction . Therefore, the limit does NOT exist.

**Remark**: If along the axis or , the limit are all equal to . So the fact that the limit exists in all coordinate directions does not imply existence of the limit.

After some rolling updates, my computer running Arch Linux fails to boot up. It turns out to be pretty hard to lock down the specific update that is causing the problem, since rebooting is done only once several weeks. After trying different things, I finally fixed it using what is described below.

The Error comes after a warning saying “modules.devname not found – ignoring”. Then “ERROR: Unable to find root device” pops out and it drops into a recovery shell, where even the keyboard does not work.

In my case, the kernel gets installed to /boot, so after a kernel update, so until manually updated, mkinitcpio will generate incorrect initramfs files.

If your computer is still on, simply run as root

mkinitcpio -p linux

and the problem will be gone (supposed to be handled automatically by pacman maybe??

However, if you did not realise doing so until the computer fails to boot up like in my case, you will have to boot into a live CD or live USB, chroot into the system, and excute the command above.

Using chroot is kind of the last resort. To do that, you may follow the following steps:

- Step 1: Prepare a live USB using Arch Linux ISO (can be downloaded from Arch download site)
- Step 2: Boot into the live USB and chroot into the system (follow for example this link.
- Step 3: Do the dirty things and reboot.

The cluster is running: bash 4.1.2, Binutils 2.20.51.0.2, bison 2.4.1, bzip2 1.0.5, Coreutils 8.4, diff 2.8.1, find 4.4.2, Gawk 3.1.7, GCC 4.4.7, Glibc 2.12, grep 2.6.3, gzip 1.3.12, Linux kernel 2.6.32, m4 1.4.13, Make 3.81, patch 2.6, Perl 5.10.1, sed 4.2.1, tar 1.23, makeinfo 4.13, xz 5.0.5. I am tring the following three approaches:

Linuxbrew is a fork of Homebrew for use on Linux systems. It would be nice if it works since it contains lots of packages.

The problem is that Linuxbrew depends on more recent versions of Ruby and Git. After compiling them from source I was able to install Linuxbrew, but cannot install any package from there due to pkg-config issues.

Spack is developed by LLNL for package managing by using explicit RPATH.

Installing environment-modules fails. The errors all seem to be associated with LMSPLIT_SIZE. This variable is used to solve the problem that some early SunOS C-shells couldn’t handle env.vars. that is too long. It seems that the cluster does not need to do the splitting, but the configure script fails to realise that. One way to fix this is to edit the package to feed –without-split-size to the configure script.

References: Deal.II in Spack. Spack Documentation.

Note: On Mac, spack’s zlib formula seems invalid. One way to fix it is to replace the download link to releases on Github. Also, to compile xz, I had to undef HAVE_CLOCK_GETTIME manually in configured header files (since the configure script failed to do so).

Caveat: There is currently no GLIBC package in Spack.

Motivated by this blog post by Tim, it is possible to build an embedded linux from scratch and use stuff from there.

However, the linker on the cluster failed to link GCC 6.2.0. (access beyond end of merged section). Reason is unknown.

TODO: try earlier versions of LFS to see if it works.

]]>

First of all, find the drive being plugged.

cat /proc/partitions

Then, mount it somewhere

mkdir -p /media/something mount /dev/driveName /media/something

After you are done with the drive, unmount it before unplugging

umount /media/something]]>

With this simple implementation of Sieve method, you can easily generate lists of prime numbers under in less than a second.

View the code on Gist.

The function is templatized by the upper bound of prime numbers looked upon. This allows the use of std::bitset for better memory efficiency. It is not particularly optimised, however, for cache missing etc. Note that the template parameter is set to be type int, using larger numbers like long int may result in stack overflow. One solution is to use dynamic allocation.

Compile with `g++ -std=c++14 main.cpp`

. Run with `time ./a.out > prime_list.txt`

, yielding (on my dual-core laptop):

real 0m0.288s user 0m0.154s sys 0m0.131s

Interestingly, the compiler seems to understand the concurrency within this code and parallelizes the work really well. Even if there is no explicit threading, the real time is roughly double the user time.

If you want to get more juice out of your machine CPU, check out PrimeSieve. It intended to be a highly optimised sieve of Eratosthenes implementation.

]]>