C程序代写-CSC209 Image Filtering Learning Objectives

CSC209 Software Tools and Systems Programming
CSC209 Image Filtering Learning Objectives
At the end of this assignment students will be able to write a program that creates new processes
manage communication between processes using pipes
read, write, and manipulate binary data
read and add to a medium-sized C program
(Update Nov 8): Additional tips posted on the Announcements page!
In this assignment, you’ll build a simple pipeline for manipulating bitmap image les by applying a set of common lters on the images, which will allow the user to do things like turn the image to grayscale, blur the image, and increase the image size.
Each image lter will be a separate program that reads in a bitmap image from its standard input, calculates some transformation on the image’s pixels and possibly its dimensions, and then writes a transformed bitmap image to its standard output.
Because we want to provide a convenient interface to the user to run several lters on a single image, you will also create a “master” program that spawns a separate process for each lter the user speci es. This program will also perform some basic process management, waiting for all of its child processes to complete, and reporting any errors that occur.
Do a in your repository to nd the starter code for assignment 3.
Also, we strongly suggest rst completing Lab 5 if you haven’t yet done so. This will make sure you are familiar with the
bitmap le format we are using for this assignment.
Starter code overview
Here is a brief description of the les found in the starter code for this assignment. Please note that unlike previous assignments, you will be creating brand-new les, not just adding to existing ones!
and : de nitions of the main types and functions used in this assignment. Look for s here to ll in the required functionality for processing bitmap les.
NOTE: there’s a small typo in that doesn’t a ect compilation, but you should change to make the code clearer. The prototype of should be
: a skeleton le for the simplest image lter you’re writing. You’ll be completing this le, and adding four more similar ones.
git pull
c void run_filter(void (*filter)(Bitmap *), int scale_factor);
11/30/2017 CSC209 Image Filtering – CSC209
: a very incomplete “master” program that manages a pipeline of image lters. You don’t have to worry about this le until Part 2.
: an incomplete make le that you (and we) will use to compile the di erent executables in this assignment. We’ve also provided a basic target that you should extend to automate some basic tests of your lters as you work through this assignment.
: a sample bitmap image le you can use for testing. Feel free to add your own! (Updated Nov 7: this le was provided right in the directory, not under .)
General C code guidelines
We have the following expectations for all source code you submit for this assignment:
1. Perform error-checking on system and library calls and use perror to print good error messages.
2. Explicitly free all dynamically-allocated memory before a program terminates.
3. Explicitly close all unused pipe ends, for every process.
4. Don’t modify/delete any of the provided functions/structs in the starter code unless we say that you can.
Part 1: Image lters
Your rst task is to complete a set of image lter programs, described below. Each lter will have the same base structure, but will di er in the actual pixel value calculations they perform, and how many pixels they need to bu er for their calculations.
Bitmap le format
11/30/2017 CSC209 Image Filtering – CSC209
We are using the same standard for bitmap images as Lab 5: 24-bit bitmap les whose width and height are divisible by 4. From the bitmap header section, you will again need to access the header size and image width and height. In addition to these three integers, you will also need to access the image le size, which is an integer stored at o set 2 in the bitmap header.
Your rst task should be to complete the function in bitmap.c . This reads in the bitmap metadata from standard input, which is necessary to complete all of the lters for this part of the assignment.
(Updated) Checkpoint!
Even without implementing the copy lter, you should be able to run the starter program and have the header data be written to stdout. You can use this to check your by redirecting this output to a le, and comparing it against the given bitmap’s header (they should be the same).
You can use to inspect each le separately (use to inspect just the rst 54 bytes). Or, you can use to compare the two les byte-by-byte (use ) to compare just the rst 54 bytes.
Image lter structure
Unlike Lab 5, in which you read in a bitmap image from a le, here you will read in the data from standard input. And because each program must write out a complete bitmap le, you must write out all of the header data as well.
Because we expect these programs to be chained together with pipes, it would be rather ine cient to always read in the entire image le (including all its pixel data), and then perform some computations on the pixels, and the write out the entire output le. All of the lters you’ll be implementing are local lters, meaning each computed pixel value will be based on at most a few surrounding pixels, and will not require reading in more than a few pixel rows of the image before being able to start computing. To take advantage of this, you’ll use implement simple bu ering approach for each lter, which is loosely described as follows:
1. Read in all of the header data, and extract the necessary image metadata described above.
-N 54
-n 54
11/30/2017 CSC209 Image Filtering – CSC209
2. Write out all of the header data for the transformed image le. In most cases, the output header will be exactly the same as the input header; for the scaling transformations, the le size and image dimensions will need to be updated.
3. Read in a number of pixels (speci ed for each lter below).
4. Compute the values for the transformed pixel(s), and write out these new pixels.
5. Repeat steps 3-4 until the entire input image has been processed, and all the new pixels written out.
Of course, the key questions are:
How do we compute the values of the transformed pixels?
How many pixels do we need to read in step 3 before computing the transformed pixel values?
These questions depend on the exact lter being used, and we’ll describe each one separately. Note that we specify the exact executable name in each case; for all of them besides , you should create and submit a new C source le that compiles to the required executable, and add the compilation recipe to your Make le.
Individual pixel lters: and
The two simplest lters operate on one pixel at a time. Your loop in this case can read in and write out exactly one pixel in each iteration.
The lter leaves the pixels unchanged; this is a good one to get started, because you simply need to read in one pixel and then immediately write it back out. Running
should product an exact copy of the original bitmap le.
$ mkdir images # Create a folder for generated images to avoid clutter. $ ./copy < dog.bmp > images/dog_copy.bmp
11/30/2017 CSC209 Image Filtering – CSC209
The lter turns the image into a black-and-white version by transforming each pixel into a new pixel , where the blue, green, and red values of the new pixel are all equal to the average of the blue, green, and red values of the original pixel, rounded down to the nearest integer. You should do normal integer arithmetic on the individual pixel elds
to compute the average:
Basic image convolutions:
works just ne.
(p.blue + p.green + p.red) / 3
The next two lters compute a transformation on a pixel from the pixel values of and the eight pixels surrounding p , i.e., the 3-by-3 grid of pixels centred on . For example, the pixel at position (2, 3) in the image is transformed based
on the following nine pixel values:
(1, 2) (1, 3) (1, 4)
(2, 2) (2, 3) (2, 4)
(3, 2) (3, 3) (3, 4)
But because the pixels in a bitmap le are stored in rows, we require a few rows of pixel data to be read in before any transformation can begin. The main loop for these two lters reads in pixels by row: at each iteration, your program should be store exactly three rows of pixels from the original image, and using these pixels to calculate and print the transformed values for every pixel in the middle row.
We have given you the code that computes the pixel transformations for you; they involve some technical calculations that are beyond the scope of this course, but you can learn about in a course like CSC320 (Introduction to Visual Computing). Instead, your main job here will be to manage the bu ering of the pixel data, and guring out how to invoke the provided functions to compute the correct pixel transformations. Read about what these functions expect in bitmap.h .
Note about boundaries: because each of these lters compute transformations based on each pixel’s neighbours, the pixels at the very edge of the image pose a problem (they don’t have neighbours on one or more sides). For simplicity on this assignment, resolve this simply by making every “edge” pixel have the exact same transformed value as its “inner” neighbour. For example, the pixel at position (0, 5) should have the same transformed value as the pixel (1, 5), and the pixel at position (0, 0) should have the same transformed value as the pixel (1, 1). If the image width is 200, the pixel at position
11/30/2017 CSC209 Image Filtering – CSC209
(199, 3) should have the same transformed value as the pixel (198, 3). You may nd the provided and macros helpful for handling these boundary pixels elegantly.
If you’re interested in reading more about image convolutions, try the Wikipedia page. Scaling
The last lter is used to scale an existing image. It takes one command-line argument , which must be an integer greater than 0. The image produced by this lter should be the same as the original image, except its width and height are multiplied by the provided scale factor. You may assume this command-line argument is always provided, and is always valid (no error-checking is required for this).
The pixel at position in the scaled image should equal the pixel at position (i / scale_factor, j / scale_factor) in the original image. Note that this is integer division, which rounds down. (This is the simplest form of scaling, and it doesn’t produce very smooth-looking images. There are more complex algorithms for scaling you’ll learn about in courses like CSC320.)
In order for the output bitmap to be valid, you’ll need to update three parts of the bitmap header before writing it to stdout: the image width, image height, and the total le size. Note that the header’s size does not change with this transformation, and so you can compute the new le size by adding the header size to the total space required to store all the pixels in the image.
Note: due to the structure of the provided function, you’ll need some way to access the input scale factor when calculating and writing the transformed pixels. There are a few di erent ways to do this (feel free to choose from the following):
1. Save this value in a global variable in your source le. 2. Modify the struct to store this data.
(i, j)
11/30/2017 CSC209 Image Filtering – CSC209
3. Do not use at all, and instead use your own modi ed version that makes the scale factor more accessible to the lter itself. This might require updating as well.
We strongly encourage you to test each image lter separately as you complete it. At the bottom of the starter , we’ve provided a target with a simple example command of one of the lters. If you add more commands to this rule, you’ll have a convenient way to run simple tests on di erent executables, just by running !
You should even be able to run multiple lters in a pipeline using standard shell syntax, e.g.
which should produce a big, blurry, grey dog.
(Updated) Here are links to sample outputs for each of the non- lters run on the provided bitmap le:
$ ./gaussian_blur < dog.bmp | ./gaussian_blur | ./gaussian_blur | ./greyscale | scale 2 > imag
make test
(scale factor of 2)
Part 2: Managing multiple lter processes
The second part of this assignment is to complete the program arguments:
, which takes at least two command-line
11/30/2017 CSC209 Image Filtering – CSC209
1. Its rst two command-line arguments specify lename for the input and output images, respectively.
2. The remaining arguments each specify the one of the ve image lter programs you developed in Part 1.
If the user wants to run the scaling lter, this must be speci ed in a command-line argument that contains “scale “ and a scale factor, e.g. .
If no arguments are provided, a single lter is performed. is responsible for doing the following:
1. Create one new process for each lter speci ed by the command-line arguments.
2. Connect the processes properly to each other (and to the input and output les) using pipes. Remember that each lter process can only communicate using its stdin/stdout, meaning that must be used to redirect each of their stdins and stdouts.
The lters must process the image in the same order the command-line arguments are speci ed by the user.
3. Wait for all processes to complete, and print a success message to the user. If one or more of the processes failed (exit with non-zero status), print a warning message to the user. We’ve provided string constants for these messages for you in the starter code.
For example, the command
should result in the same behaviour (except the output message) as
“scale 2”
$ ./gaussian_blur < dog.bmp | ./gaussian_blur | ./gaussian_blur | ./greyscale | ./scale 2 > im
$ ./image_filter dog.bmp images/dog_piped.bmp ./gaussian_blur ./gaussian_blur ./gaussian_blur
11/30/2017 CSC209 Image Filtering – CSC209
(Updated Nov 7: the above command was previously missing one invocation of ; there should be three invocations of it, not two.)
Commit all your code to your repository. Running should produce six executables: the ve image lters , , , , and (check their names carefully!) and the master
executable. You are welcome to commit sample test les that you used.
Note: it is generally not good practice to commit the .o or executable les to your repository, as these les should be automatically generated from your source code. If you accidentally committed such les, please remove them from your repo ( ) before your nal submission.
git rm
© 2017 Karen Reid | Powered by Jekyll on GitHub Pages


电子邮件地址不会被公开。 必填项已用*标注