Bad code analysis -- "we wrote the book C language (Second Edition)" 21 point pr

Recommended for you: Get network issues from WhatsUp Gold. Not end users.

  Analysis of this code to the following. In order to illustrate the problem, add the line numbers for the code.

0. #include <stdio.h>
1. #include <time.h>
2. #include <ctype.h>
3. #include <stdlib.h>
4. 
5. #define BELL '\a'
6. #define DEALER 0
7. #define PLAYER 1
8. 
9. #define ACELOW 0
10. #define ACEHIGH 1
11. 
12. int askedForName = 0;
13. 
14. void dispTitle(void);
15. void initCardsScreen(int cards[52],int playerPoints[2],
16. int dealerPoints[2], int total[2], 
17. int *numCards);
18. int dealCard(int * numCards,int cards[52]);
19. void dispCard(int cardDrawn,int points[2]);
20. void totalIt(int points[2],int tatal[2],int who);
21. void dealerGetsCard(int *numCards,int cards[52],
22. int dealerPoints[2]);
23. void playerGetsCard(int *numCards,int cards[52],
24. int playerPoints[2]);
25. char getAns(char mesg[]);
26. void findWinner(int total[2]);
27. 
28. main()
29. {
30.    int numCards;
31.    int cards[52],playerPoints[2],dealerPoints[2],total[2];
32.    char ans;
33. 
34.    do 
35.    { 
36.       initCardsScreen(cards,playerPoints,dealerPoints,total, &numCards);
37.       dealerGetsCard(&numCards,cards, dealerPoints);
38.       printf("\n");
39.       playerGetsCard(&numCards,cards,playerPoints); 
40.       playerGetsCard(&numCards,cards,playerPoints);
41.       do
42.       {
43.          ans = getAns("Hit or stand (H/S)?");
44.          if ( ans == 'H' )
45.          { 
46.             playerGetsCard(&numCards,cards,playerPoints);
47.          }  
48.       }
49.       while( ans != 'S' );
50. 
51.       totalIt(playerPoints,total,PLAYER);
52.       do
53.       {
54.          dealerGetsCard(&numCards,cards,dealerPoints);
55.       }
56.       while (dealerPoints[ACEHIGH] <17 );
57. 
58.       totalIt(dealerPoints,total,DEALER);
59.       findWinner(total); 
60. 
61.       ans = getAns("\nPlay again(Y/N)?");  
62.    }
63.    while(ans=='Y');
64. 
65.    return ;
66. 
67. }
68. 
69. void initCardsScreen( int cards[52],int playerPoints[2],
70.                       int dealerPoints[2], int total[2], 
71.                       int *numCards )
72. {
73.    int sub,val = 1 ;
74.    char firstName[15];
75.    *numCards=52;
76. 
77.    for(sub=0;sub<=51;sub++)
78.    {
79.       val = (val == 14) ? 1 : val;
80.       cards[sub] = val;
81.       val++;  
82.    }
83. 
84.    for(sub=0;sub<=1;sub++)
85.    { 
86.       playerPoints[sub]=dealerPoints[sub]=total[sub]=0;
87.    }
88.    dispTitle();
89. 
90.    if (askedForName==0)
91.    { 
92.       printf("What is your first name?");
93.       scanf(" %s",firstName);
94.       askedForName=1;
95.       printf("Ok, %s,get ready for casino action!\n\n",firstName);
96.       getchar();
97.    }
98.    return;        
99. }
100. 
101. void playerGetsCard(int *numCards,int cards[52],int playerPoints[2])
102. {
103.    int newCard;
104.    newCard = dealCard(numCards, cards);
105.    printf("You draw:");
106.    dispCard(newCard,playerPoints);
107. }
108. 
109. 
110. void dealerGetsCard(int *numCards,int cards[52],int dealerPoints[2])
111. {
112.    int newCard;
113.    newCard = dealCard(numCards,cards);
114.    printf("The dealer draws:");
115.    dispCard(newCard,dealerPoints);
116. }
117. 
118. int dealCard(int * numCards,int cards[52])
119. {
120.    int cardDrawn,subDraw;
121.    time_t t;
122.    srand(time(&t));
123.    subDraw = (rand()%(*numCards));
124.    cardDrawn = cards[subDraw];
125.    cards[subDraw] = cards[*numCards -1];
126.    (*numCards)-;
127.    return cardDrawn;
128. }
129. 
130. void dispCard(int cardDrawn, int points[2])
131. {
132.    switch(cardDrawn)
133.    {
134.       case(11): printf("%s\n","Jack");
135.                 points[ACELOW] += 10;
136.                 points[ACEHIGH] += 10;
137.                 break;
138.       case(12): printf("%s\n","Queen");
139.                 points[ACELOW] += 10;
140.                 points[ACEHIGH] += 10;
141.                 break;
142.       case(13): printf("%s\n","King");
143.                 points[ACELOW] += 10;
144.                 points[ACEHIGH] += 10;
145.                 break;
146.       default : points[ACELOW] += cardDrawn;
147.                 if(cardDrawn==1)
148.                 { 
149.                    printf("%s\n","Ace");
150.                    points[ACEHIGH]+= 11;
151.                 }
152.                 else
153.                 {  
154.                   points[ACEHIGH]+=cardDrawn;
155.                   printf("%d\n",cardDrawn); 
156.                 }
157.    }
158.    return ;
159. }
160. 
161. void totalIt(int points[2],int total[2],int who)
162. {
163.    if ( (points[ACELOW] == points[ACEHIGH])
164.       ||(points[ACEHIGH] > 21 ))
165.    { 
166.      total[who] = points[ACELOW];
167.    }
168.    else
169.    { 
170.        total[who] = points[ACEHIGH];
171.    }
172. 
173.    if (who == PLAYER )
174.    {
175.       printf("You have a total of %d\n\n", total[PLAYER]);
176.    }
177.    else
178.    {
179.        printf("The house stands with a total of %d\n\n", 
180.        total[DEALER]);
181.    }
182.    return;
183. }
184. 
185. void findWinner(int total[2])
186. {
187.    if ( total[DEALER] ==  21 )
188.    {
189.        printf("The house wins.\n");
190.        return ;
191.    }
192.    if ( (total[DEALER] > 21) && (total[PLAYER] > 21) )
193.    { 
194.       printf("%s", "Nobody wins.\n");
195.       return ; 
196.    }
197.    if ((total[DEALER] >= total[PLAYER])&& (total[DEALER] <21))
198.    { 
199.       printf("The house wins.\n");
200.       return ; 
201.    }
202.    if ((total[PLAYER] > 21)&& (total[DEALER] <21))
203.    { 
204.       printf("The house wins.\n");
205.       return ; 
206.    }
207.    printf("%s%c","You win!\n",BELL);
208.    return;
209. }
210. 
211. char getAns(char mesg[])
212. {
213.    char ans;
214.    printf("%s", mesg);
215.    ans = getchar();
216.    getchar();
217.    return toupper(ans);
218. }
219. 
220. void dispTitle(void)
221. {
222.    int i = 0 ;
223.    while(i<25)
224.    { 
225.         printf("\n");
226.         i++; 
227.    }
228.    printf("\n\n*Step right up to the Blackjack tables*\n\n");
229.    return ;
230. }

  First look at the main () function.

31.    int numCards;
32.    int cards[52],playerPoints[2],dealerPoints[2],total[2];
33.    char ans;

  The 31 and 32 rows are the basic data object, the program processing in contrast, 33 lines define variables of ANS than the ant (ANT) is also small, than chicken ribs is boring, talks to the reason behind.

  main()Function mainly said a word (the other one is a commonplace talk of an old scholar return 0;), is a DO-WHILE statement:


35.    do 
36.    { 
        /*……*/
62.       ans = getAns("\nPlay again(Y/N)?");  
63.    }
64.    while(ans=='Y');

  It is the intention to achieve in the game after the game, selected by the user end program or continue to the next round of the game. But in fact this sentence actually don't need the ANS variables, code can be more succinctly written as:


35.    do 
36.    { 
        /*……*/
63.    }
64.    while( getAns("\nPlay again(Y/N)?") == 'Y' ) ;

  The solution to a problem may have many kinds of methods, the most simple that is the right way. Occam's razor tells us, if not necessary, do not increase the entity. Simplicity is an important spiritual characteristics of C language.

  It is not difficult to see that the 33 line definition of variables is completely superfluous.

(to be continued)

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download

Posted by Winfred at November 13, 2013 - 8:34 AM