On financial independence

To achieve financial independence, a state in which one’s asset generates more interest than one’s expense, it is generally assumed that one has to save early and save big, due to the power of compounding. This depends on one critical assumption, that the rolling return over 30 years remains largely the same regardless of the entry point in a 30 year period. Although accurate prediction of future returns is difficult to perform, computer simulations could be more easily applied to past data to confirm the assumption.

Data TBD by Miaomiao. 

Personal Goals:

  • Control monthly expense under 5k.
  • Based on this expense and the 4% rule, 1.5 M is needed to achieve perpetual financial freedom.
  • Achieve financial independence by age 40.
  • Save 71k per year after year, plus 401(k).

Skills to be developed by MM:

  • Trading/investment skills
  • General machine learning

Skills to be developed by TT:

  • Deep learning
  • Computer vision
  • Skills that is not employer specific, such as software development skills, apps development, English skills, speech skills.
Posted in Uncategorized | Leave a comment

installation of tensorflow on windows or MacOS

Windows:

I had the following error when installing tensorflow on windows 7 (Python 3.5.2 :: Anaconda 4.1.1 (64-bit))

Cannot remove entries from nonexistent file d:\anaconda32\envs\tst\lib\site-pack
ages\easy-install.pth

This is a anaconda environment problem. I found the solution here:

pip install --ignore-installed --upgrade pip setuptools
pip install --upgrade tensorflow

Now add the python from anaconda package permanently to cygwin.

echo 'export PATH=/cygdrive/c/anaconda3:$PATH' >> .bashrc

MacOS

Install TensorFlow in virtualenv to avoid version contamination.

mkvirtualenv cv -p python3
workon cv
pip3 install --upgrade tensorflow # for Python 3.n

Validate the installation

import tensorflow as tf
hello = tf.constant('Hello, TensorFlow!')
sess = tf.Session()
print(sess.run(hello))

Run a test model

git clone https://github.com/tensorflow/models.git
cd ~/TensorFlow/models/tutorials/image/imagenet
python classify_image.py --image_file ~/TensorFlow/daisy.jpeg

TBD

Posted in Uncategorized | Leave a comment

Affine and Perspective Transformation

In affine transformation (link, link2), all parallel lines in the original image will still be parallel in the output image. To find the transformation matrix, we need 3 points from input image and their corresponding locations in output image. Then cv2.getAffineTransform will create a 2×3 matrix which is to be passed to cv2.warpAffine. Affine transform can perform rotation, translation, resizing,

pts1 = np.float32([[50,50],[200,50],[50,200]])
pts2 = np.float32([[10,100],[200,50],[100,250]])

M = cv2.getAffineTransform(pts1,pts2)
dst = cv2.warpAffine(img,M,(cols,rows))

For perspective transformation (see links above), you need a 3×3 transformation matrix. Straight lines will remain straight even after the transformation. To find this transformation matrix, you need 4 points on the input image and corresponding points on the output image. Among these 4 points, 3 of them should not be collinear. Then transformation matrix can be found by the function cv2.getPerspectiveTransform. Then apply cv2.warpPerspective with this 3×3 transformation matrix.

pts1 = np.float32([[56,65],[368,52],[28,387],[389,390]])
pts2 = np.float32([[0,0],[300,0],[0,300],[300,300]])

M = cv2.getPerspectiveTransform(pts1,pts2)
dst = cv2.warpPerspective(img,M,(300,300))

In summary,

  • Affine transformation preserves lines and parallelism.
  • Perspective transformation preserves lines. Affine transform is a special case of perspective transformation.
  • PS, affine transformation does not preserve angle. Conformal transformation preserves angle.

 

Posted in openCV, Uncategorized | Tagged , | Leave a comment

Important concepts in CV

This post serves as a list of miscellaneous techniques that litters in the CV field. They are not listed in any particular order for now.

  1. Hard-negative mining. For each image and each possible scale of each image in your negative training set, apply the sliding window technique and slide your window across the image. At each window compute your HOG descriptors and apply your classifier. If your classifier (incorrectly) classifies a given window as an object (and it will, there will absolutely be false-positives), record the feature vector associated with the false-positive patch along with the probability of the classification. This approach is called hard-negative mining. Take the false-positive samples found during the hard-negative mining stage, sort them by their confidence (i.e. probability) and re-train your classifier using these hard-negative samples. (Note: You can iteratively apply steps 4-5, but in practice one stage of hard-negative mining usually [not not always] tends to be enough. The gains in accuracy on subsequent runs of hard-negative mining tend to be minimal.)
  2. Non-Maximum Suppression (link) can be used if multiple bounding boxes are returned for the same detected object.
  3. find bounding shapes (openCV link): boundingRect() finds the up-right bounding rectangle of a point set, minAreaRect() finds the rotated bounding rectangle of a point set which is often used with boxPoints() returning the four vertices of the rectangle, minEnclosingTriangle() finds the bounding triangle with min area, minEnclosingCircle() finds the bounding circle with min area.
  4. overlapping object detection, use watershed algorithm (openCV tutorial, PIS tutorial).
  5. Thresholding is to reduce a gray scale image to a binary image. Automatic (parameterless) threshold detection is usually more computationally intensive than those requiring a manual tuning process. Two widely used methods are Otsu’s method and Ridler-Calvard’s method, both of which are histogram-based thresholding method.
  6. The Otsu’s method assumes the pixels in a gray scale image are divided into two classes, the foreground and the background, following a bimodal histogram and finds the global optimal threshold to minimize the intra-cluster variance, or equivalently, maximize the inter-cluster variance. However, when the image background is uneven, finding a global threshold that generates good results may simply be impossible. This original method can be extended to a 2D Otsu’s adaptive method which find local threshold based on the gray scale value of each pixel and the average of its neighboring pixels. This can help greatly with noise corrupted images or images with uneven background (nonuniform illumination). Theoretically any method used for estimating the threshold can be made adaptive if applied locally in a block-wise or sliding window fashion, but the computational cost may be quite high, such as the 2D Otsu’s method. Ridler-Calvard’s method is an iterative version of Otsu’s method, and is generally faster and less computationally intensive as Otsu’s method.
  7. Drawbacks of Otsu’s method: it assumes the histogram is bimodal; it applies a global threshold and thus does not work with uneven background; it breaks when the two classes have extremely different sizes.
  8. Multilevel thresholding can be applied when there are more than 2 modes in the histogram, but it proves to be more difficult in practice.
  9. Histogram-based thresholding methods works the best when histogram peaks are tall, narrow, symmetric, and separated by deep valleys. If there is no clear valley in the histogram, that means there are background pixels with similar gray levels with object pixels. In this case, hysteresis thresholding which employs two threshold values, one at each side of the valley can be used. The threshold ratio is generally between 2:1 and 3:1. In hysteresis thresholding, low thresholded edges which are connected to high thresholded edges are retained. Low thresholded edges which are non connected to high thresholded edges are removed. Hysteresis thresholding is the only method that considers some form of spatial proximity. Other methods completely ignores spatial information.
  10. Niblack’s method is a much less computationally intensive version, which finds the local threshold to be t(i, j) = μ(i, j) + wσ(i, j), using a weighted average of local mean and standard deviation, but w need to be tuned manually.
  11. Edge detection employs gradients to find edge-like regions. The Sobel operator finds the partial derivatives of the image along the x- and y-axes by convolving with a ksize x ksize kernel. When ksize is 3, Sobel operator may generate noticeable inaccuracies. A similar Scharr operator is as fast but generates more accurate results. Laplacian operator adds up the second order derivatives along the x- and y-axes calculated by the Sobel operator.
  12. Canny detector is also called optimal detector, which has low error rate, good localization and minimal response. It has four steps: Filter out noise, find the intensity gradient of the image, apply non maximum suppression (only thin lines will remain), apply hysteresis thresholding using two thresholds.
  13. Contours can be found by calling cv2.findContours() function, which takes an input image of 8-bit single channel (grayscale) image. The image is treated as binary since nonzero values are treated as one. This binary image can be generated using threshold(), adaptiveThreshold() or Canny(), etc. The contour finding algorithm uses this algorithm and returns a topological hierarchy of contours.
  14. to be continued…
Posted in Uncategorized | Leave a comment

ML notes

ROC curve characterizes the performance of a binary classifier as its discrimination threshold varies. It plots the true positive rate (TPR) against the false positive rate (FPR). In other words, it plots the recall/sensitivity against the (1-specificity).

 

 

Posted in Uncategorized | Leave a comment

points and matrix accessing order in openCV

In openCV,

  • Points is in the order of (x,y);
  • Size is in the oder of (width,height);
    However,
  • Matrix is accessed in the order of (row,col)
  • Image is stored in the order of (height, width)

For example, in

cv2.resize(image, dsize, interpolation=cv2.INTER_AREA)

dsize is the output (destination, ergo d) image size in the order of (width, height).

cv2.warpAffine(image, M, dsize)

M is the 2×3 transformation matrix, dsize is the output image size in the order of (w, h). According to the documentation of warpAffine,

x' = M_11 * x + M_12 * y + M_13
y' = M_21 * x + M_22 * y + M_23

where (x, y) is the coordinates of the source pixel, and (x’, y’) is the coordinate for the destination of the warp.

Using the affine transform matrix M, we can take care of scaling, rotation, translation at the same time. However, since the increasing y direction is downward in an image, the rotational matrix is

[M_11, M_12] = [ cos(theta),  sin(theta)]
[M_21, M_22]   [-sin(theta),  cos(theta)]

which is different from the rotational matrix for the Cartesian system

[M_11, M_12] = [ cos(theta), -sin(theta)]
[M_21, M_22]   [ sin(theta),  cos(theta)]

An easy way to remember this is, a point at (x, y) = (1, 1) will be rotated 45 degrees to (1.4, 0) on the x-axis, not y-axis, as it would be in the Cartesian system.

Posted in Uncategorized | Leave a comment

Why openCV uses BGR (not RGB)

When using openCV to load an image, the color information is stored in the order of Blue-Green-Red instead of the currently more popular scheme RGB.

http://www.pyimagesearch.com/2014/11/03/display-matplotlib-rgb-image/

import cv2
image = cv2.imread(args["image"])
cv2.imshow("Image" , image)
cv2.waitKey(0)

This reads in and displays the correct image file. An alternative way to do this using matplotlib is as follows.

import matplotlib.image as mpimg
image = mpimg.imread(args["image"])
plt.axis("off")
plt.imshow(image)
# plt.imshow(cv2.cvtColor(image, cv2.COLOR_BGR2RGB))
plt.show()

However, if we read in the image file through cv2 and display it with matplotlib or vice versa, the image will not be displayed correctly, since the R and B channels are flipped (see above link for an example image). Luckily, cv2 has a built-in way to correct this.

import cv2
import matplotlib.image as mpimg
image = cv.imread(args["image"])
plt.axis("off")
plt.imshow(cv2.cvtColor(image, cv2.COLOR_BGR2RGB))
plt.show()

Alternatively, we can hack this by swapping the B and R channel since it is the third dimension of the image.

image = image[:, :, ::-1] # or image = image[:, :, (2, 1, 0)]
plt.imshow(img)

According to the following post, BGR was introduced to the openCV in a time when BGR was the most popular format, and it got stuck. It is very similar to the funny story why US railway gauge is 4’8.5″.

http://www.learnopencv.com/why-does-opencv-use-bgr-color-format/

 

Posted in openCV, python | Tagged , , | Leave a comment