{}[ ( ) ] {{ [ []() ] }} {
}
Each of the following four lines is unbalanced:
{ (} - left paren and right curly bracket don't match
[ () } - left square brace and right curly bracket don't match
} - no left curly bracket
() ( [] ) ( - no right paren
If standard input is balanced,
the program should print out the number of each pair seen.
If not, the program should print out what the error is, and on what
lines the mismatch occurred.
For example, look at the files input1, input2, input3, and input4.
Input1 is a C program where everything is balanced. When you run bal_paren on it, the output should look like:
UNIX> bal_paren < input1
Parentheses (): 26
Square braces []: 3
Curly brackets {}: 5
UNIX>
Almost all C programs are balanced.
The other three input files have the three types of unbalances that your program needs to catch -- unmatched '(', '[' or '}', unmatched ')', ']' or '}', and mismatches. For example, input2 has three unmatched characters (read the file to see which ones):
UNIX> bal_paren < input2 Unmatched symbols: [ on line 3 ( on line 2 ( on line 1 UNIX>Input3 has an unmatched right paren:
UNIX> bal_paren < input3 Unmatched ) on line 3 UNIX>and input4 has a mismatch on lines 1 and 2
UNIX> bal_paren < input4
Mismatch: { on line 1 and ] on line 2
UNIX>
Obviously, the TA's will test more than just these input files. So should you.
You need to use dllists to write bal_paren. The concept is simple -- when you see a left paren, square brace or curly bracket, you bundle up that character with its line number (i.e. you'll have to malloc() a struct) and prepend it to the dllist. When you see a right paren, square brace or curly bracket, you first see if the list is empty. If so, you have an unmatched character that you flag and then exit. Next, you pop off the first element of the list (you'll be using the .v field of the Jval). If the character in the struct matches the current character (for example the character in the struct is a left paren and the current character is a right paren), then you have a match, and everything is fine -- go ahead and free() the struct. If they don't match, then you have discovered a mismatch and can print it out and exit. When you are done reading standard input, if there are any structs left on the list, then they are unmatched. If the list is empty, you can conclude that the input was balanced.
This is a moderate-sized program -- mine was 84 lines without comments.
So, for example, using the Music.txt file from the lecture notes on information hiding, we get the following:
UNIX> music_find Cars < Music.txt Cars 1 12 9 Hello_Again 3:44 Cars,_The Heartbeat_City Rock 1 Drive 3:51 Cars,_The Heartbeat_City Rock 4 Let's_Go 3:34 Cars,_The Sounds_of_the_Seventies_-_1979,_Take_Two Rock 1 Good_Times_Roll 3:44 Cars,_The The_Cars Rock 1 My_Best_Friend's_Girl 3:41 Cars,_The The_Cars Rock 2 Just_What_I_Needed 3:40 Cars,_The The_Cars Rock 3 I'm_In_Touch_With_Your_World 3:27 Cars,_The The_Cars Rock 4 Don't_Cha_Stop 3:03 Cars,_The The_Cars Rock 5 You're_All_I've_Got_Tonight 4:12 Cars,_The The_Cars Rock 6 Bye_Bye_Love 4:12 Cars,_The The_Cars Rock 7 Moving_In_Stereo 4:39 Cars,_The The_Cars Rock 8 All_Mixed_Up 4:10 Cars,_The The_Cars Rock 9 She_Has_Funny_Cars 3:12 Jefferson_Airplane Surrealistic_Pillow Rock 1 UNIX> music_find Cars < Music.txt Heartbeat Cars 1 12 9 Heartbeat 2 0 2 Hello_Again 3:44 Cars,_The Heartbeat_City Rock 1 Drive 3:51 Cars,_The Heartbeat_City Rock 4 Let's_Go 3:34 Cars,_The Sounds_of_the_Seventies_-_1979,_Take_Two Rock 1 Good_Times_Roll 3:44 Cars,_The The_Cars Rock 1 My_Best_Friend's_Girl 3:41 Cars,_The The_Cars Rock 2 Just_What_I_Needed 3:40 Cars,_The The_Cars Rock 3 I'm_In_Touch_With_Your_World 3:27 Cars,_The The_Cars Rock 4 Don't_Cha_Stop 3:03 Cars,_The The_Cars Rock 5 You're_All_I've_Got_Tonight 4:12 Cars,_The The_Cars Rock 6 Bye_Bye_Love 4:12 Cars,_The The_Cars Rock 7 Moving_In_Stereo 4:39 Cars,_The The_Cars Rock 8 All_Mixed_Up 4:10 Cars,_The The_Cars Rock 9 She_Has_Funny_Cars 3:12 Jefferson_Airplane Surrealistic_Pillow Rock 1 Heartbeat 3:48 Riggs Heavy_Metal Rock 2 Turn_That_Heartbeat_over_Again 4:59 Steely_Dan Can't_Buy_A_Thrill Rock 10 UNIX> music_find Blues < Music.txt | head -5 Blues 80 7 54 West_Coast_Blues 4:02 Adderly,_Cannonball African_Waltz Jazz 2 Come_And_Go_Blues 4:55 Allman_Brothers Brothers_and_Sisters Rock 3 Statesboro_Blues 4:19 Allman_Brothers Sounds_of_the_Seventies,_Guitar_Power Rock 6 UNIX> grep Jazz Music.txt | music_find Blues | head -5 Blues 57 0 38 West_Coast_Blues 4:02 Adderly,_Cannonball African_Waltz Jazz 2 Wild_Man_Blues_[2nd_Take] 3:06 Armstrong,_Louis Highlights_From_His_Decca_Years,_Disc_1 Jazz 1 Weary_Blues 2:48 Armstrong,_Louis Highlights_From_His_Decca_Years,_Disc_1 Jazz 2 UNIX> music_find _I_ Love Cake < Music.txt | head -5 _I_ 118 20 27 Love 318 0 45 Cake 7 0 8 I'm_Not_in_Love 3:47 10cc Sounds_of_the_Seventies_-_1975,_Take_Two Rock 21 UNIX> music_find I Love Cake < Music.txt | head -5 I 1570 120 1036 Love 318 0 45 Cake 7 0 8 UNIX>
This is a pretty straightforward program. You'll need a Dllist to hold the lines of matched songs, and three arrays to hold the number of matches for each command line argument. My solution was 58 lines.