Edit this page Backlinks This page is read only. You can view the source, but not change it. Ask your administrator if you think this is wrong. ====== 7. Working with matrices and images using higher-order functions ====== ===== 7.1. Bitmaps as matrices ===== We can represent images as matrices of pixels. In our example a pixel will be represented as a ''Char'', which can take the values: '*' (signifying that the respective pixel is //on//) and ' ' (the pixel is off). <code haskell> type Image = [String] </code> For instance, a rectangle could be represented as: <code> ******** * * ******** </code> more precisely, as the string: <code haskell> m = "********\n* *\n********\n" </code> 7.1.1. Implement an image-displaying function. Use the image from the Appendix as a test. <code haskell> toStringImg :: Image -> String toStringImg = </code> Add the following function in order to view images in a nicer format: <code haskell> displayImg = putStrLn . toStringImg </code> 7.1.2. Implement a function which flips an image horizontally: <code haskell> flipH :: Image -> Image flipH = </code> 7.1.3. Implement a function which flips an image vertically: <code haskell> flipV :: Image -> Image flipV = </code> 7.1.4. Implement a function which rotates an image 90grd clockwise <code haskell> rotate90r :: Image -> Image rotate90r = </code> 7.1.5. Implement a function which rotates an image -90grd clockwise <code haskell> rotate90l :: Image -> Image rotate90l = </code> 7.1.6. Implement a function which inverts an image: ' ' becomes * and * becomes ' ': <code haskell> invert :: Image -> Image invert = </code> ===== 7.2. Combining images ===== 7.2.1. Implement a function ''maskKeep'' which takes a mask and some image and only keeps the part of image which overlays the mask. Use the mask and the logo from Appendix to test it. <code haskell> maskKeep :: Image -> Image -> Image maskKeep = </code> $math[ maskKeep \left(\begin{array}{ccc} & & * \\ & & * \\ & & * \\ \end{array}\right) \left(\begin{array}{ccc} * & & * \\ * & & \\ * & & * \\ \end{array}\right) = \left(\begin{array}{ccc} & & * \\ & & \\ & & * \\ \end{array}\right) ] 7.2.2. Implement a function ''maskDiscard'' which takes a mask and some image and discards the part of the mask which overlays the image. $math[ maskDiscard\left(\begin{array}{ccc} & & * \\ & & * \\ & & * \\ \end{array}\right) \left(\begin{array}{ccc} * & & * \\ * & & \\ * & & * \\ \end{array}\right) = \left(\begin{array}{ccc} & & \\ & & * \\ & & \\ \end{array}\right) ] 7.2.3. Implement the ''union''' of two images. <code haskell> unionp :: Image -> Image -> Image unionp = </code> $math[ union \left(\begin{array}{ccc} & & * \\ & & * \\ & & * \\ \end{array}\right) \left(\begin{array}{ccc} * & & * \\ * & & \\ * & & * \\ \end{array}\right) = \left(\begin{array}{ccc} * & & * \\ * & & * \\ * & & * \\ \end{array}\right) ] 7.2.4. Implement a function which takes a list of transformations and an image and applies all those transformations. <code haskell> transformationSequence :: [Image -> Image] -> Image -> Image </code> Test it with the following sequence <code haskell> seq1 = transformationSequence [invert, unionp mask, rotate90r] </code> ===== 7.3 Number Matrices ===== 7.3.1. Write a function that computes the scalar product with an integer: $math[ \displaystyle 2 * \left(\begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 \\ \end{array}\right) = \left(\begin{array}{ccc} 2 & 4 & 6 \\ 8 & 10 & 12 \\ 14 & 16 & 18 \\ \end{array}\right)] <code haskell> vprod :: Integer -> Matrix -> Matrix vprod v = </code> 7.3.2. Write a function which adjoins two matrices by extending rows: $math[ \displaystyle \left(\begin{array}{cc} 1 & 2 \\ 3 & 4\\\end{array}\right) hjoin \left(\begin{array}{cc} 5 & 6 \\ 7 & 8\\\end{array}\right) = \left(\begin{array}{cc} 1 & 2 & 5 & 6 \\ 3 & 4 & 7 & 8\\\end{array}\right) ] <code haskell> hjoin :: Matrix -> Matrix -> Matrix hjoin = </code> 7.3.3. Write a function which adjoins two matrices by adding new rows: $math[ \displaystyle \left(\begin{array}{cc} 1 & 2 \\ 3 & 4\\\end{array}\right) vjoin \left(\begin{array}{cc} 5 & 6 \\ 7 & 8\\\end{array}\right) = \left(\begin{array}{cc} 1 & 2 \\ 3 & 4 \\ 5 & 6\\ 7 & 8\\ \end{array}\right) ] <code haskell> vjoin :: Matrix -> Matrix -> Matrix vjoin = </code> 7.3.4. Write a function which adds two matrices. <code haskell> msum :: Matrix -> Matrix -> Matrix msum = </code> ===== Appendix ===== <code haskell> logo = [l1,l2,l3,l4,l5,l6,l7,l8,l9,l10,l11,l12,l13,l14,l15,l16,l17,l18,l19] where l1 =" ***** ** ***** ** " l2 =" ****** **** ****** **** " l3 =" ** * * *** ** * * *** " l4 =" * * * *** * * * *** " l5 =" * * ** * * ** " l6 =" ** ** ** ** ** ** " l7 =" ** ** ** ** ** ** " l8 =" **** ** * **** ** * " l9 =" * *** ** * * *** ** * " l10=" ** ******* ** ******* " l11=" ** ****** ** ****** " l12=" ** ** ** ** " l13=" ** ** ** ** " l14=" ** ** ** ** " l15=" ** ** ** ** ** ** " l16="*** * * *** * * " l17=" *** * *** * " l18=" ****** ****** " l19=" *** *** " </code> <code haskell> mask = [l1,l2,l3,l4,l5,l6,l7,l8,l9,l10,l11,l12,l13,l14,l15,l16,l17,l18,l19] where l1 =" *****************" l2 =" *****************" l3 =" *****************" l4 =" *****************" l5 =" *****************" l6 =" *****************" l7 =" *****************" l8 =" *****************" l9 =" *****************" l10=" *****************" l11=" *****************" l12=" *****************" l13=" *****************" l14=" *****************" l15=" *****************" l16=" *****************" l17=" *****************" l18=" *****************" l19=" *****************" </code>