<jupyter_start><jupyter_text>$\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;$ HW 1   CS484 - CS555 Introduction to Computer Vision>Dr. <NAME> >Submission Deadline:  23:55, February 28th, 2021  - After  that  time, late submissions will receieve 25% penalty per additional day!>TA e-mails: >> Akif: <EMAIL>>Submission link: (Submit your HW through this link:)  https://forms.gle/o2yEBmaseok1eGbk9 __________________________________________________________________________________________  Running your code on Google Colab*  It is strongly advised that you first go through the links below and familiarize yourself with the Colab environment. * You should first load this HW file (HW1.ipynb) on Google Colab ( https://colab.research.google.com ) and run it on Google Colab which acts as a remote server since we will also test your code on Colab. Then go through the links below to get a better understanding of Colab environment.* Note that you can run this file on your local jupyter notebook as well, however, we will test your submissions on Google Colab and your code and submitted notebook is expected to run on Google Colab. It is student's responsibility to make sure that his/her submitted file will run on Colab without any error.Useful links (You should go through the links below to get introductory material for Colab and image processing with Python):* https://web.eecs.umich.edu/~justincj/teaching/eecs498/FA2020/colab.html* https://colab.research.google.com/github/cs231n/cs231n.github.io/blob/master/python-colab.ipynb* https://colab.research.google.com/drive/1b8pVMMoR37a3b9ICo8TMqMLVD-WvbzTk* There are many Colab tutorials available on Youtube. Here is a short video: https://www.youtube.com/watch?v=inN8seMm7UI and another video: https://www.youtube.com/watch?v=i-HnvsehuSw  __Instructions and Notes on Answering Your Homework__ * Save a copy of your own HW1.ipynb file locally and save that file in the following format: ***FullName_StudentID_HW1.ipynb***, where FullName is your name and surname respectively, and StudentID is your student ID number. Then you can upload that file on Colab.* Use the submission link (see above for the link) to submit your solutions.Email your solution to the TA ( <EMAIL> ) with the email subject: ***FullName_CS484CS555_HW1***; in which ***FullName*** is your name and surname. Your file(s) need to be compressed as a single ***zip*** file containing both your .ipynb file (including your saved results).* You will be graded for your implementation, results and also for a brief explanation of your answer, if asked.* An implementation that is not generating the correct result, may not receive any credit. To get full credit for a question, you need to follow all the instructions given for that question and provide all the required discussions and results correctly.* We will run your code on Colab. Make sure that your code runs without any  error on Colab.* All submissions must have your own code/implementation. To get ideas, you can discuss with your friends. But, your submission needs to be your own work.* Cheating will be punished as described on the course website.* In questions 2, 3, 4, 5 and 6 you need to use grayscale versions of the given images as input (a given RGB image must be converted into a grayscale image first).* SUBMIT  YOUR SOLUTIONS (your new .ipynb file) as a zip file (as described above) at: https://forms.gle/o2yEBmaseok1eGbk9*  Late submissions will receive %25 per day passing the submission deadline.  __Question 1 - Warm up - Read, save and show images__ (5 points) OpenCV is a big and well-known library containing a large set of Computer Vision and Image Processing related functions. In this part of the assignment, you will learn to apply some basic functions of opencv on images. * First read the `Q1.png` and then, reduce its size by dividing its height and width by 3 and display that new resized image (with figure name 'resized image'). You need to save your resized image as `img01_1.jpg`.  * Next, convert your original input image (`Q1.png`) into grayscale and do the same operations (with figure name 'gray and resized image') on the grayscale image and display it.For loading an image on Colab - you can check the following two sites to get ideas:* https://datascience.stackexchange.com/questions/29480/uploading-images-folder-from-my-system-into-google-colab*  https://towardsdatascience.com/the-2-step-guide-to-upload-images-in-google-colab-b51348e882e4<jupyter_code>#implement and run your python code for Question 1 in this box (here).

# You can use the sample code snippet below as a STARTING POINT! 
# (Feel free to edit or delete the code snippet below!)
import cv2 as cv 
import matplotlib.pylab as plt
from google.colab import drive
from google.colab.patches import cv2_imshow

drive.mount('/content/drive', force_remount=True)
# Note: Check the path of the HW1 files first, AFTER uploading them on your own google drive 
# and replace the path below with the actual one on your own google drive, if it differs.  
image = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q1.png') 
image = cv.resize(image, (500, 300)) 
cv2_imshow(image)<jupyter_output>Mounted at /content/drive<jupyter_text>__Question 2 - Image histogram__ (10 points) In this part, you will compute and display the histogram of a grayscale image. A histogram is a graph that shows the total number of pixels for each intensity value of an image. It gives you an idea about the intensity distribution of a given image. * Compute and plot the histogram of the following images: `Q1.png`, `Q2.png`, `Q2_2.png`Then compare and **discuss** your results in the text box that was given below the code box.* You must implement the histogram computing part yourself; you can not use any libraries' built-in function to compute the histogram.<jupyter_code>##put and run your code for Question 2 here

# first read the images: Q1.png, Q2.png and Q2_2.png

#calculate and plot the histogram of each image (with titles Q1, Q2, Q2_2 respectively), and display their histograms.


# You can use the sample code below to COMPARE your own implementation of histogram
#____________________
im02 = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q1.png') 
im03 = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q2.png') 
im04 = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q2_2.png') 

im02_gray = cv.cvtColor(im02, cv.COLOR_BGR2GRAY) 
im03_gray = cv.cvtColor(im03, cv.COLOR_BGR2GRAY) 
im04_gray = cv.cvtColor(im04, cv.COLOR_BGR2GRAY) 

plt.figure(figsize=([15, 5]))

plt.subplot(131), plt.hist(im02_gray.ravel(),bins = 256, range = [0,256]) 
plt.subplot(132), plt.hist(im03_gray.ravel(),bins = 256, range = [0,256]) 
plt.subplot(133), plt.hist(im04_gray.ravel(),bins = 256, range = [0,256]) 
plt.show()<jupyter_output><empty_output><jupyter_text>In this cell (in this text box), show and compare all three histograms. Discuss the difference(s) between dark and bright images in terms of histogram.--Double click on this text and discuss your results by typing HERE (in this box) --  __Question 3 - Histogram equalization Part A__ (15 points) * In this part, you will implement histogram equalization (for a grayscale image) to enhance the contrast in an image. Histogram equalization distributes the existing intensities on an image to a larger range so that all intensity values are used, as much as possible. Use images: `Q2.png` and `Q2_2.png` for this question.* Based on the results you obtain, discuss whether it is a good idea to use histogram equalization on all images in general.* You can not use openCV's (or any other libraries') built-in function to equalize histograms; you need to implement the histogram equalization part by yourself here. Also, you are not allowed to compute the histogram using built-in histogram functions either. You need to use your own implemantation of histogram computing from the previous question.Helpful sites:* https://en.wikipedia.org/wiki/Histogram_equalization* https://www.math.uci.edu/icamp/courses/math77c/demos/hist_eq.pdf* http://www.sci.utah.edu/~acoste/uou/Image/project1/Arthur_COSTE_Project_1_report.htmlequalization<jupyter_code># implement and run your code for Question 3a below 


# display the original grayscale image and the result with titles "original grayscale image", "equalized image" respectively
# display them in subplots, in which the first subplot is original image,
# second subplot is the result after applyiny histogram equalization.
#_____________________________
im2 = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q2.png')
im3 = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q2_2.png') 


# Show both images and their histogram equalized versions below<jupyter_output><empty_output><jupyter_text>Discuss here if histogram equalization seems like a good solution for any and all types of images (based on the results you see from the given two images).  __Question 3 - Histogram equalization Part B__ (5 points) 1. In this part, you will compute the histogram equalization again on the same images that you used in the previous part (`Q2.png`, `Q2_2.png`). The only difference is that, this time, you are allowed to use OpenCV's built-in histogram equalization function. 2. After you apply the histogram equalization on both images, compare your results with the results obtained in the previous question (Question 3a). * Use subplots for showing the four results together. The first subplot is the result image from part "a" for image `Q2.png` with title 'Q2 equalized'. The second subplot is the result from part "a" for image `Q2_2.png` with title 'Q2_2 equalized'. The third subplot is the result image from part "b" for image `Q2.png` with title 'Q2 equalized OpenCV'. The fourth subplot is the result image from part "b" for image `Q2_2.png` with title 'Q2_2 equalized OpenCV'.* Also, plot the histogram of `Q2_2.png` before applying histogram equalization and the histogram of resulting image after applying histogram equalization on the same image. Show both histograms side by side in a single Figure.  Helpful sites: * https://opencv-python-tutroals.readthedocs.io/en/latest/py_tutorials/py_imgproc/py_histograms/py_histogram_equalization/py_histogram_equalization.html<jupyter_code># put and run your code for Question 3b here<jupyter_output><empty_output><jupyter_text>__Question 4 - Otsu's thresholding__ (15 points) * Implement automated thresholding by Otsu’s Method. You must use your own implementation and avoid using any image processing libraries (except for reading and plotting images). Your function declaration should take a grayscale image (a 2D matrix) as an input and produce a binary image (also a 2D matrix) of the same dimensions as in the input image. Use the format below:` binary_image = otsu_threshold(source_image)`* Separate the background from the foreground using your implementation of Otsu’s algorithm. Show the binary mask and the original input image side by side. Test your results on both `Q2.png` and `Q2_2.png` files. Discuss your results, are they always perfect? Why so, why not?* Use image: `Q1.png` and after applying Otsu's thresholding on the image,  **show only the clouds** by removing the content of tree from the image (i.e., do not show the actual pixels that belog to a tree). (All the pixels that belong to a tree can be artificially colored with a fix color value).Useful links:* https://en.wikipedia.org/wiki/Otsu%27s_method* http://www.labbookpages.co.uk/software/imgProc/otsuThreshold.html* https://opencv-python-tutroals.readthedocs.io/en/latest/py_tutorials/py_imgproc/py_thresholding/py_thresholding.html<jupyter_code># implement your function below.





# See the OpenCV sample below that computes and compares three different thresholding technique on the same input image. 
# This code example uses OpenCV's built-in functions. HOWEVER, you need to implement OTSU's technique by yourself.
# the first thresholding below is the standard thresholding technique where we enter the threshold values manually,
# the second thresholding below is the OTSU's technique. 
# Change the image path according to your own Google drive structure!
img = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q1.png')
img = cv.cvtColor(img, cv.COLOR_BGR2GRAY) 
# global thresholding
ret1,th1 = cv.threshold(img,10,255,cv.THRESH_BINARY)

# Otsu's thresholding
ret2,th2 = cv.threshold(img,0,255,cv.THRESH_BINARY+cv.THRESH_OTSU)


# plot all the images and their histograms
images = [img, 0, th1,
          img, 0, th2]
titles = ['Original Image','Histogram','Manuel Thresholding',
          'Original Image','Histogram',"Otsu's Thresholding"]

plt.imshow(th1,'gray')

for i in [0,1]:
    plt.subplot(3,3,i*3+1),plt.imshow(images[i*3],'gray')
    plt.title(titles[i*3]), plt.xticks([]), plt.yticks([])
    plt.subplot(3,3,i*3+2),plt.hist(images[i*3].ravel(),256)
    plt.title(titles[i*3+1]), plt.xticks([]), plt.yticks([])
    plt.subplot(3,3,i*3+3),plt.imshow(images[i*3+2],'gray')
    plt.title(titles[i*3+2]), plt.xticks([]), plt.yticks([])
plt.show()

#Now lets show the result obtained with Otsu's technique in a larger frame. 
height, width = th2.shape[:2]
th2 = cv.resize(th2, (int(width/4), int(height/4))) 
cv2_imshow(th2) 


# Here you can test your function on the given binary image and see the result
img = cv.imread('/content/drive/My Drive/CS484-CS555/HW1-Spring2021/images/Q1.png')
img = cv.cvtColor(img, cv.COLOR_BGR2GRAY) 
binary_image = otsu_threshold(img)
cv2_imshow(binary_image)<jupyter_output><empty_output><jupyter_text>__Question 5 - Morphological Operators - Part A: Implement Dilation__ (15 points) In  this section, you will first implement Dilation operator as a function. In your function, you will take two inputs (as matrices): (i) the input image as a matrix and (ii) a structuring element (also as a matrix), and produce a binary image (another matrix) as output. Note that the resulting image matrix should be of the same size as input image matrix. As before, in your function, your methods should be generic, that is it should work with grayscale image and structuring element of any size. Your method declaration should look as follows:`dilated_image = dilation (source_image , structuring_el )`* You should generate the structuring element (kernel) as a binary image with an arbitrary shape (you can use 3 by 3 square matrix with all 1s **for testing**). * Given the structuring element, your code should implement the dilation operation by using the definitions given in the course slides. Note that the structuring element should be created (as a matrix) outside and given as an input to the dilation/erosion codes so that your code can work with any kind of structuring element. You can assume that the origin is in the center, or get the coordinate of the origin as a separate input to your functions.<jupyter_code>## implement your python function for dilation  here
# 
#
# test your dilation function here on 3b.png with a 3x3 structuring element (matrix) with all 1s.<jupyter_output><empty_output><jupyter_text>__Question 5 - Morphological Operators - Part B: Implement Erosion__ (15 points) Similar to the previous question, you will also implement a morphological operator here. This time, you will implement Erosion operator as a function. In your function, you will take two inputs (as matrices): (i) the input image as a matrix and (ii) a structuring element (also as a matrix), and produce a binary image (another matrix) as output. Note that the resulting image matrix should be of the same size as input image matrix. As before, in your function, your methods should be generic, that is it should work with grayscale image and structuring element of any size. Your method declaration should look as follows:`eroded_image = erosion ( source_image , structuring_el )`* You should generate the structuring element (kernel) as a binary image with an arbitrary shape (you can use 3 by 3 square matrix with all entries being 1 **for testing**). * Given the structuring element, your code should implement the erosion operation by using the definitions given in the course slides. Note that the structuring element should be created (as a matrix) outside and given as an input to the dilation/erosion codes so that your code can work with any kind of structuring element. You can assume that the origin is in the center, or get the coordinate of the origin as a separate input to your functions.<jupyter_code># implement your erosion operator here
#
#


# test your erosion function here on a binary image with a 3x3 structuring element (matrix) with all 1s.
#<jupyter_output><empty_output><jupyter_text>__Question 6 - Combine multiple techniques__ (20 points + 10 bonus points = 30 points) In this question, you will use your previously implemented functions. You are provided with 2 gray scale images: `3a.png` and `3b.png` for this question. You are expected to apply a sequence of thresholding, reqion growing and/or morphological operations to segment and count distinct objects in the given image individually.* The first step is to find (by trial and error or by using Otsu’s method), a threshold that will produce a binary image that best separates objects from the background. Please, specify which method you are using and specify why.* The second step is to use the morphological operators (dilation, erosion and their combinations) you have implemented, to help separate objects that are connected together or to fill holes in the objects. Note that you might need to use inverse operation on the binary image of the planes as they are painted in white against black background. * Once you have a decent binary image, use region growing or (connected components labeling) to produce a labeled image that has a distinct label (an integer ID) for each region.* You MUST use your own dilation, erosion and thresholding implementations. You CAN use other sources (such as OpenCV) for arithmetic and logical operators, connected components labeling, region growing, and image I/O. Note that you are NOT allowed to use any operator other than the ones listed above.* Note that you will have to provide analytical justification for the specific sequence of operations performed and what each step achieves. Simply providing a working sequence is not enough. It is also possible that several different sequences achieve desired result, you are encouraged to find and compare them on your own. But report only one such sequence.<jupyter_code>## Implement and run your code here<jupyter_output><empty_output><jupyter_text>Double click and discuss your techniques and results HERE for Question 6.  Grading  $\;\;\;\;\;\;\;\;\;\;\;$ a $\;\;\;\;\;\;\;\;\;$ b $\;\;\;\;\;\;\;\;\;$ c $\;\;\;\;\;\;\;\;\;$ d  Q1Q2   Q3Q4  Q5  Q6***__Total__: /100<jupyter_code><jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.07884625506605611, 'fraction_numerical': 0.021737986209800515, 'mean_word_length': 4.835380835380835, 'pattern_counts': {'":': 0, '<': 39, '<?xml version=': 0, '>': 45, 'https://': 15, 'lorem ipsum': 0, 'www.': 5, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '9', 'dir': 'jupyter-structured-clean-dedup', 'id': '486175', 'license': 'Apache-2.0', 'n_tokens_mistral': 5587, 'n_tokens_neox': 5177, 'n_words': 2485, 'path': 'Hw1/Assignment/HW1-Spring2021/HW1.ipynb', 'repo_name': 'cankocagil/CompVision', 'size': '19047'}