home *** CD-ROM | disk | FTP | other *** search
/ 8bitfiles.net/archives / archives.tar / archives / genie-commodore-file-library / Information / C.TUTOR.2.SFX / lesson11 < prev    next >
Encoding:
Text File  |  1991-03-07  |  17.5 KB  |  790 lines

  1.  
  2. ├ ╠ANGUAGE ╘UTORIAL
  3. -------------------
  4. ╨ART 11 OF 11
  5.  
  6.  
  7. ╬╧╘┼: ╙╒┬╙╘╔╘╒╘╔╧╬╙ ╞╧╥ ╙╨┼├╔┴╠ ├
  8. ╠┴╬╟╒┴╟┼ ├╚┴╥┴├╘┼╥╙:
  9.  
  10. ╠┼╞╘ ├╒╥╠┘ ┬╥┴├╦┼╘:   █
  11. ╥╔╟╚╘ ├╒╥╠┘ ┬╥┴├╦┼╘:  ▌
  12. ┬┴├╦ ╙╠┴╙╚:           \
  13. ╘╔╠─┼:                »
  14. ╓┼╥╘╔├┴╠ ┬┴╥:         ▀
  15. ╒╬─┼╥╙├╧╥┼:           ñ
  16.  
  17.  
  18. ╙╘╥╒├╘╒╥┼╙ -
  19.  
  20. ╔F WE WISH TO KEEP A RECORD OF, SAY, 
  21. FRIENDS ... INCLUDING NAME, ADDRESS, 
  22. BIRTHDATE, ETC. WE MIGHT DECLARE: 
  23.  
  24. CHAR NAME[20]; 
  25. CHAR ADDRESS[40]; 
  26. CHAR BIRTHDATE[15];
  27.  
  28. ...WHERE NAME, FOR EXAMPLE, IS AN 
  29. ARRAY OF 20 CHARACTERS WHICH IS MEANT 
  30. TO HOLD THE NAME OF ONE SUCH FRIEND, 
  31. AND ADDRESS HOLDS 40 CHARS, ETC. ╔F 
  32. WE WANT 100 SUCH RECORDS, WE COULD 
  33. USE: 
  34.  
  35. CHAR NAME[100][20]; 
  36. CHAR ADDRESS[100][40]; 
  37. CHAR BIRTHDATE[100][15];
  38.  
  39. ...WHERE NAME[0], NAME[1],NAME[2], 
  40. ETC. ARE EACH ARRAYS OF 20 
  41. CHARACTERS, ETC. 
  42.  
  43. ╫E WOULD PRINT OUR LIST VIA A 
  44. STATEMENT LIKE: 
  45.  
  46. FOR (I=0; I<100; I++) 
  47. PRINTF("\N%S %S %S", NAME[I],
  48.        ADDRESS[I],BIRTHDATE[I]);
  49.  
  50. ╙INCE THE BIRTHDATE HAS THE FORM "╬OV 
  51. 6, 1934" (FOR EXAMPLE) WE WOULD NEED 
  52. TO EXTRACT THE LAST NUMBER ( 1934), 
  53. AND PERFORM A SUBTRACTION, IN ORDER 
  54. TO DETERMINE HIS (HER?) AGE ... AND 
  55. WOULD NEED ALL SUCH NUMBERS IN ORDER 
  56. TO DEDUCE THE AVERAGE AGE OF OUR 
  57. FRIENDS. ╙O WE MIGHT DECLARE 
  58. BIRTHDATE TO BE A TRIO OF OBJECTS: AN 
  59. ARRAY OF CHARACTERS (TO HOLD THE 
  60. BIRTH-MONTH, LIKE "╬OV"), AN INTEGER 
  61. (TO HOLD THE BIRTH-DAY) AND A SECOND 
  62. INTEGER (TO HOLD THE BIRTH-YEAR) ... 
  63. THAT WAY WE COULD PERFORM SOME 
  64. ARITHMETIC ON THE INTEGER PARTS OF 
  65. THE BIRTHDATE. 
  66.  
  67. CHAR NAME[100][20], ADDRESS[100][40];
  68. CHAR BIRTH_MONTH[100][4];
  69. INT  BIRTH_DAY[100], BIRTH_YEAR[100];
  70.  
  71. ╘HE ABOVE WOULD DO IT. ╙UFFICIENTLY 
  72. MANY ARRAYS (OF CHARACTERS AND 
  73. INTEGERS) FOR 100 FRIENDS, EACH WITH 
  74. NAMES OF  19  CHARACTERS (OR LESS) 
  75. AND ADDRESSES OF  39  CHARACTERS (OR 
  76. LESS) AND  3  CHARACTERS FOR THE 
  77. BIRTH_MONTH (WE'LL NEED THE 
  78. TERMINATING '\0' IN EACH CHAR ARRAY!) 
  79. ...AND 100 BIRTH_DAYS AND BIRTH_YEARS 
  80. (REMEMBER THAT BIRTH_DAY[0] TO 
  81. BIRTH_DAY[99] IS 100 BIRTH-DAYS!) 
  82.  
  83.  
  84. ╔T WOULD BE NICE TO HAVE A ─┴╘┴ ╘┘╨┼ 
  85. WHICH HELD ONE SUCH RECORD, WITH 
  86. NAME, ADDRESS, ETC. AND MIXED CHARS 
  87. AND INTS !! 
  88.  
  89.  
  90.  
  91. ...LET'S WELCOME THE ╙╘╥╒├╘╒╥┼ -
  92.  
  93. ╔T IS SOMETIMES HELPFUL TO THINK OF A 
  94. STRUCTURE AS A TYPE OF ARRAY WHICH 
  95. CAN HOLD VARIABLES OF DIFFERING 
  96. TYPES. 
  97.  
  98. ╫E INVENT A STRUCTURE CALLED DATE 
  99. WHICH INCLUDES A 3 CHARACTER MONTH
  100. ( HENCE MONTH[4] ) AND TWO INTS 
  101. (DAY AND YEAR). 
  102.  
  103. ╫E ARE ACCUSTOMED TO SAYING INT X; 
  104. AND CHAR Y;, MEANING THAT X IS OF 
  105. ─┴╘┴ ╘┘╨┼ INT AND Y IS OF ─┴╘┴ ╘┘╨┼ 
  106. CHAR. ╙╧, WE WILL WANT TO SAY DATE 
  107. BIRTH; MEANING THAT BIRTH IS OF ─┴╘┴ 
  108. ╘┘╨┼ DATE MEANING A COLLECTION OF 
  109. OBJECTS: 
  110.  
  111. A CHAR MONTH[4], AN INT DAY, 
  112. AND AN INT YEAR.
  113.  
  114. ┬UT, IF DATE IS A STRUCTURE (WITH THE 
  115. ELEMENTS MENTIONED ABOVE) THEN WE 
  116. WILL REFER TO IT AS STRUCT DATE, TO 
  117. INFORM THE COMPILER THAT DATE IS NO 
  118. ORDINARY GUY BUT IS, IN FACT, A 
  119. STRUCT ... 
  120.  
  121.  
  122. ╙╧, WE DECLARE BIRTH TO BE SUCH A 
  123. STRUCTURE (CALLED DATE) VIA: 
  124.  
  125. STRUCT DATE BIRTH;  
  126.  
  127. ╙O WHY WOULDN'T WE JUST DEFINE A 
  128. STRUCTURE CALLED BIRTH, WHICH HAS THE 
  129. 3 MEMBERS: MONTH[4] AND INT DAY AND 
  130. INT YEAR ?? 
  131.  
  132. ┬ECAUSE WE WILL WANT TO USE THIS 
  133. STRUCT FOR OTHER DATES, LIKE: 
  134.  
  135. STRUCT DATE DEATH;
  136.  
  137. ╘OO MORBID?  ╘HEN HOW ABOUT:
  138.  
  139. STRUCT DATE ╫HEN╫E═ET;
  140.  
  141. ╬OW, ╫HEN╫E═ET IS OF ─┴╘┴ ╘┘╨┼ DATE 
  142. TOO, CONTAINING THE SAME 3 ELEMENTS 
  143. OF CHAR MONTH[4] AND INT DAY AND INT 
  144. YEAR !! 
  145.  
  146. (╬OTE: SOME COMPILERS MAY NOT 
  147. RECOGNIZE NAMES LIKE ╫HEN╫E═ET BUT 
  148. MAY RESTRICT NAMES TO, SAY, 8 
  149. CHARACTERS OR LESS). 
  150.  
  151.  
  152.  
  153. ╔NSIDE A ╙╘╥╒├╘URE -
  154.  
  155. ┬EFORE WE SEE HOW TO DEFINE SUCH A 
  156. STRUCTURE AS DATE, LETS SEE HOW IT 
  157. COULD BE USED. ╔T WILL HAVE 3 
  158. MEMBERS: MONTH, DAY, YEAR.
  159. ╫E DECLARE: 
  160.  
  161. STRUCT DATE BIRTH[100], ╫HEN╫E═ET[100];
  162.  
  163. ...SO EACH OF BIRTH[0], BIRTH[1], 
  164. ETC. AND ╫HEN╫E═ET[0], ╫HEN╫E═ET[1], 
  165. ETC. ARE STRUCTS OF ╘┘╨┼ DATE. 
  166.  
  167. ╘HE WAY TO GET ACCESS TO THE MEMBERS
  168. OF A STRUCTURE IS TO USE THE NAME OF
  169. THE STRUCTURE FOLLOWED BY A PERIOD
  170. FOLLOWED BY THE NAME OF THE MEMBER
  171. OF THE STRUCTURE. ╞OR EXAMPLE, TO
  172. ACCESS THE CHAR VARIABLE 'MONTH' IN
  173. THE FIFTY-FOURTH 'BIRTH' STRUCTURE
  174. WE WOULD SAY:
  175.  
  176. CHAR *PC;
  177. PC = BIRTH[54].MONTH;
  178.  
  179. ...NOW THE POINTER-TO-CHAR 'PC'
  180. POINTS TO WHAT WE WANT TO ACCESS.
  181.  
  182. ╫E REFER TO BIRTH[I].MONTH, 
  183. BIRTH[I].DAY AND BIRTH[I].YEAR AND TO 
  184. ╫HEN╫E═ET[I].MONTH, ╫HEN╫E═ET[I].DAY 
  185. AND ╫HEN╫E═ET[I].YEAR FOR I=0, 1, 2, 
  186. ... UP TO THE NUMBER OF FRIENDS WE 
  187. HAVE ...AND EACH REFLECTS THE 3 
  188. MEMBERS MONTH, DAY AND YEAR OF THE 
  189. DATE STRUCTURE.
  190.  
  191. ╘O INPUT ALL THIS INFORMATION WE 
  192. MIGHT USE: 
  193.  
  194. PRINTF("\N ╬UMBER OF FRIENDS: "); 
  195. SCANF("%S",&NUMBER); 
  196. /* HERE WE ASK FOR THE NUMBER OF 
  197. FRIENDS, AND STORE IT IN NUMBER */
  198. FOR (I=0; I<NUMBER; I++) █
  199. /* THEN,WE GO THROUGH EACH OF NUMBER
  200. OF FRIENDS, ASKING QUESTIONS */
  201. PRINTF("\N ╞OR FRIEND %D",I); 
  202. /* REMIND THE USER WHICH FRIEND WE
  203. ARE WORKING ON BY PRINTFING ...   
  204. ╞OR FRIEND 1:  THEN,
  205. ╞OR FRIEND 2:  ETC. */
  206. PRINTF("\N ┼NTER ═ONTH OF ┬IRTH ");
  207. SCANF("%S",&BIRTH[I].MONTH); 
  208. /* ASK  ┼NTER ═ONTH OF ┬IRTH  AND 
  209. PUT THE ANSWER INTO &BIRTH[I].MONTH
  210. (FOR THE ITH FRIEND) AND, AS 
  211. REQUIRED BY SCANF(),WE USE THE 
  212. &ADDRESS ! */
  213. PRINTF("\N ┼NTER ─AY   OF ┬IRTH ");
  214. SCANF("%S",&BIRTH[I].DAY);
  215. PRINTF("\N ┼NTER ┘EAR  OF ┬IRTH ");
  216. SCANF("%S",&BIRTH[I].YEAR);
  217. ...AND SO ON, FOR THE BIRTH.DAY AND 
  218. BIRTH.YEAR   
  219. ...UNFORTUNATELY, THIS WON'T (QUITE)
  220. WORK ...DO YOU SEE WHY?
  221.  
  222. ╘HE NUMBER BEING INPUT VIA SCANF() 
  223. SHOULD HAVE A %D (FOR AN INTEGER). 
  224.  
  225. ...BUT THERE'S SOMETHING ELSE ...
  226.  
  227. PRINTF("\N ┼NTER ═ONTH OF ┬IRTH ");
  228. SCANF("%S",&BIRTH[I].MONTH); 
  229.  
  230. SCANF() WILL PUT THE 3 CHARACTERS 
  231. TYPED AT THE KEYBOARD, SAY "╬OV", 
  232. INTO THE MEMORY RESERVED FOR 
  233. BIRTH[I].MONTH, BUT ╫╧╬'╘ PUT IN A 
  234. '\0'! ├ REQUIRES THAT ALL STRINGS
  235. BE TERMINATED WITH A ╬╒╠╠.
  236.  
  237. ╫┼ MUST PUT IT IN ( ...WHILE WE'RE 
  238. PRAYING THAT THE USER DOESN'T TYPE 
  239. NOVEMBER, WHICH IS MUCH TOO LONG TO 
  240. FIT INTO THE 4 BYTES WE'VE RESERVED 
  241. FOR THE MONTH!) 
  242.  
  243. ╫E COULD INITIALIZE ALL THE BYTES IN 
  244. THE BIRTH.MONTH TO '\0' VIA: 
  245.  
  246. FOR (I=0; I<100; I++) █
  247. /* FOR ALL 100 FRIENDS */ 
  248.   FOR (J=0; J<4; J++) █
  249. /* FOR EACH OF 4 BYTES */
  250.   BIRTH[I].MONTH+J='\0';  
  251. /* SET BYTE TO '\0' */
  252.   █  /* END OF INNER "FOR" */
  253. ▌  /* END OF OUTER "FOR" */
  254.  
  255. ... THEN (PROVIDED THE USER DOESN'T 
  256. TYPE MORE THAN A 3 CHARACTER MONTH!) 
  257. WE'VE GOT ALL THE '\0' STRING 
  258. TERMINATORS WE'LL NEED. 
  259.  
  260. ╘HIS LITTLE RITUAL IS NECESSARY 
  261. BECAUSE SCANF() IS MEANT AS A 
  262. GENERAL-PURPOSE INPUT ...INTS AND 
  263. FLOATS AND CHARS ETC. 
  264.  
  265. ┴ SPECIAL-PURPOSE INPUT ...JUST FOR 
  266. STRINGS OF CHARS ...WOULD BE SMART 
  267. ENOUGH TO APPEND THE '\0' (WOULDN'T 
  268. IT?) 
  269.  
  270. ╘HE STDIO.H LIBRARY OF ├-FUNCTIONS 
  271. WILL CONTAIN SUCH A FUNCTION. 
  272. GETS(&SAM) WILL GET A STRING AND PUT 
  273. IT INTO THE ADDRESS &SAM. ╩UST AS 
  274. SCANF() REQUIRES A POINTER TO THE 
  275. MEMORY LOCATION WHERE THE INPUT IS TO 
  276. BE STORED, SO DOES GETS(). 
  277.  
  278. ╞OR EXAMPLE, WE WRITE:
  279.  
  280. 1 PRINTF("\N ╚OW MANY FRIENDS DO 
  281.          YOU HAVE "); 
  282. 2 SCANF("%D",&NUMBER); 
  283. 3 FOR (I=0; I<NUMBER; I++) █
  284. 4 PRINTF("\N ╞OR FRIEND %D",I);
  285. 5 PRINTF("\N ┼NTER ═ONTH OF ┬IRTH "); 
  286. 6 GETS(&BIRTH[I].MONTH);   
  287. 7 PRINTF("\N ┼NTER ─AY OF ┬IRTH "); 
  288. 8 SCANF("%D",&BIRTH[I].DAY); 
  289. 9 PRINTF("\N ┼NTER ┘EAR OF ┬IRTH ");
  290. 10 SCANF("%D",&BIRTH[I].YEAR);  
  291. 11 ▌
  292.  
  293. ...AND THE GETS() IN LINE 6 WILL 
  294. COLLECT EACH CHARARACTER TYPED, AND 
  295. WHEN A \NEWLINE IS TYPED (THE ╥ETURN 
  296. OR ┼NTER KEY) IT WILL EXCHANGE IT FOR 
  297. A '\0' ...AND PUT EVERYTHING INTO THE 
  298. MEMORY LOCATION INDICATED. 
  299.  
  300.  
  301.  
  302. ─EFINING A ╙╘╥╒├╘URE -
  303.  
  304. ╔T'S ABOUT TIME WE DEFINED OUR STRUCT 
  305. DATE : 
  306.  
  307.  STRUCT DATE █
  308.    CHAR MONTH[4];   
  309.    INT DAY; 
  310.    INT YEAR;
  311.  ▌; 
  312.  
  313. ╬OTE THE STRUCTURE OF A STRUCTURE:
  314.  STRUCT NAME █
  315.    --- ALL THE ---  
  316.    --- MEMBERS ---  
  317.    --- GO HERE ---  
  318.  ▌; 
  319.  
  320. ╫E GIVE IT A NAME (LIKE DATE) SO WE 
  321. CAN DECLARE OTHER OBJECTS TO BE OF 
  322. THIS ─┴╘┴ ╘┘╨┼ ( REMEMBER BIRTH AND 
  323. ╫HEN╫E═ET ? ) 
  324. ...AND AN OPENING AND CLOSING BRACES
  325. ...AND THE VARIOUS MEMBERS (LIKE 
  326. CHAR MONTH[4], ETC.)
  327. ...AND A FINAL  ▌; 
  328.  
  329. FINAL ▌; ??
  330.  
  331.  STRUCT DATE █
  332.    CHAR MONTH[4]; 
  333.    INT DAY;   
  334.    INT YEAR;  
  335.  ▌;   
  336.  
  337. ╘HIS FINAL ▌; IS MEANINGFUL!
  338.  
  339. ┬ECAUSE A STRUCT DATE IS TO BE USED 
  340. JUST LIKE INT OR CHAR, AND BECAUSE WE 
  341. USUALLY SAY INT X; OR CHAR X; (WITH A 
  342. FINAL ;), THEN WE TERMINATE A 
  343. STRUCTURE DEFINITION WITH A ; AND 
  344. EXPECT TO BE ABLE TO SAY: 
  345.  
  346. STRUCT DATE █   
  347.   --- ETC ---  
  348.    ▌ X;  
  349. /* NOTE SIMILARITY WITH INT X; */
  350.  
  351.  
  352. ╙╧, FOR OUR EARLIER EXAMPLE, WE COULD 
  353. SAY: 
  354.  
  355.  STRUCT DATE █
  356.   CHAR MONTH[4]; 
  357.   INT DAY;   
  358.   INT YEAR;  
  359.  ▌ BIRTH[100],╫HEN╫E═ET[100]; 
  360.  
  361. ... AND WE'VE DEFINED OUR STRUCT DATE 
  362. ┴╬─ DECLARED BIRTH[] AND ╫HEN╫E═ET[] 
  363. TO BE SUCH STRUCTURES ... ALL AT 
  364. ONCE! 
  365.  
  366. ╥EMEMBER: 'DATE' IS THE NAME OF A 
  367. ╘┘╨┼ OF STRUCTURE AND THIS TYPE-NAME 
  368. OF A STRUCTURE IS CALLED A ╘┴╟.
  369. ┬OTH 'BIRTH[100]' AND 
  370. '╫HEN╫E═ET[100]' ARE NAMES OF 
  371. PARTICULAR STRUCTURES OF THE TYPE 
  372. WE'VE DEFINED AS 'DATE'. 
  373.  
  374. ╙O, YOU CAN ACHIEVE THE SAME RESULT
  375. AS ABOVE BY WRITING:
  376.  
  377.   STRUCT DATE █
  378.     CHAR MONTH[4];
  379.     INT DAY;
  380.     INT YEAR;
  381.   ▌;
  382.  
  383.   STRUCT DATE BIRTH[100],
  384.             ╫HEN╫E═ET[100];
  385.  
  386.  
  387. ╬OW LET'S RETURN TO THE RECORD OF OUR 
  388. "FRIENDS", WHICH INCLUDES NAME AND 
  389. ADDRESS AS WELL AS SOME DATES AS WELL
  390. AS A NEW ADDITION TO WHAT CAN BE DONE
  391. WITH STRUCTURES.
  392.  
  393.  
  394.  
  395. ╙TRUCTURES WITHIN ╙TRUCTURES -
  396. (NOBODY SAID THIS WAS EASY!)
  397.  
  398. ╞OR EACH "RECORD" WE WILL DEFINE 
  399. ANOTHER STRUCTURE ... LET'S CALL IT 
  400. "RECORD": 
  401.  
  402.  STRUCT  RECORD █
  403.   CHAR NAME[20];   
  404.   CHAR ADDRESS[40];
  405.   STRUC DATE BIRTH;
  406.   STRUC DATE ╫HEN╫E═ET;
  407.  ▌ FRIEND[100];
  408.  
  409. ╬OTE THAT WE'VE NOT ONLY DEFINED THE 
  410. STRUCT CALLED RECORD BUT WE'VE ALSO 
  411. DECLARED 100 SUCH STRUCTURES, USING 
  412. THE "FINAL" NAME FRIEND[100]; 
  413.  
  414. ...FRIEND[0] AND FRIEND[1] AND 
  415. FRIEND[2] ETC. ARE ┴╠╠ OF TYPE RECORD 
  416. AND HENCE CONTAIN THE MEMBERS: NAME, 
  417. ADDRESS, BIRTH AND ╫HEN╫E═ET. 
  418.  
  419.  
  420. ╘HE FIRST TWO (NAME AND ADDRESS) ARE 
  421. CHARACTER ARRAYS ┬╒╘ THE LAST TWO 
  422. (BIRTH AND ╫HEN╫E═ET) ARE ...╙╒╥╨╥╔╙┼ 
  423. (!) STRUCTURES OF ╘┘╨┼ DATE !!! 
  424.  
  425. ╫E NOW HAVE A STRUCTURE:
  426.  
  427.   STRUCT RECORD █
  428.     CHAR NAME[20];
  429.     CHAR ADDRESS[40];
  430.     STRUCT DATE █
  431.       CHAR MONTH[4];
  432.       INT DAY;
  433.       INT YEAR;
  434.     ▌ BIRTH;
  435.     STRUC DATE █
  436.       CHAR MONTH[4];
  437.       INT DAY;
  438.       INT YEAR;
  439.     ▌ ╫HEN╫E═ET;
  440.   ▌ FRIEND[100];  
  441.  
  442. ┼ARLIER WE DECLARED 200 STRUCTURES OF 
  443. ╘┘╨┼ DATE (NAMELY BIRTH[100] AND 
  444. ╫HEN╫E═ET[100]). ╫E ALSO SAW HOW TO 
  445. REFER TO THE 3 MEMBERS OF BIRTH[47] 
  446. (FOR EXAMPLE) AS BIRTH[47].MONTH, 
  447. BIRTH[47].DAY AND BIRTH[47].YEAR. 
  448.  
  449. ╔N ORDER TO ACCESS THE INT VARIABLE
  450. 'DAY' WITHIN THE THIRTY-SEVENTH 
  451. STRUCT FRIEND, WITHIN THE STRUCT 
  452. BIRTH WE WOULD SAY:
  453.  
  454. INT *PI;
  455. PI = FRIEND[37].BIRTH.DAY;
  456.  
  457. ...OR, IN A PROGRAM WHERE YOU ARE
  458. ASKING THE USER FOR INPUT YOU COULD
  459. WRITE:
  460.  
  461. PRINTF("┼NTER DAY OF BIRTH: ");
  462. GETS(&FRIEND[37].BIRTH.DAY);
  463.  
  464. ╔T IS POSSIBLE TO HAVE STRUCTURES 
  465. WITHIN STRUCTURES!! 
  466.  
  467. ╚ERE IS A NOT-TOO-USEFUL, BUT QUITE
  468. ILLUSTRATIVE, SAMPLE PROGRAM:
  469.  
  470. MAIN()
  471.   INT NUMBER, I;   
  472.   STRUCT DATE █
  473.    CHAR MONTH[4];  
  474.    INT DAY;
  475.    INT YEAR;   
  476.   ▌;
  477.   STRUCT RECORD █
  478.    CHAR NAME[20];  
  479.    CHAR ADDRESS[40];   
  480.    STRUCT DATE BIRTH;  
  481.   ▌ FRIEND[100];   
  482.   
  483.   PRINTF("\N╚OW MANY FRIENDS : ");
  484.   SCANF("%D",&NUMBER);
  485.    
  486.   FOR (I=0; I<NUMBER; I++) █
  487.    PRINTF("\N ╞OR FRIEND %D",I+1);  
  488.    PRINTF("\N╬AME? ");   
  489.    GETS(&FRIEND[I].NAME);
  490.    PRINTF("\N┴DDRESS? ");
  491.    GETS(&FRIEND[I].ADDRESS); 
  492.    PRINTF("\N═ONTH OF BIRTH? "); 
  493.    GETS(&FRIEND[I].BIRTH.MONTH); 
  494.    PRINTF("\N─AY OF BIRTH? "); 
  495.    SCANF("%D",&FRIEND[I].BIRTH.DAY);
  496.    PRINTF("\N┘EAR OF BIRTH? "); 
  497.    SCANF("%D",&FRIEND[I].BIRTH.YEAR);
  498.   ▌
  499.  
  500.  PRINTF("\N╙╒══┴╥┘ OF YOUR %D 
  501.         FRIENDS",NUMBER);
  502.  FOR (I=0; I<NUMBER; I++)█
  503.   PRINTF("\N╬AME:%S",
  504.          FRIEND[I].NAME); 
  505.   PRINTF("\N┴DDRESS:%S",
  506.          FRIEND[I].ADDRESS);   
  507.   PRINTF("\N┬ORN ON %S %D,%D",
  508.          FRIEND[I].BIRTH.MONTH,
  509.          FRIEND[I].BIRTH.DAY,
  510.          FRIEND[I].BIRTH.YEAR);
  511.  ▌
  512.  
  513.  
  514. ...GIVING A (TYPICAL) PRINTOUT:
  515.  
  516. ╬AME:╨ETER ╨ONZO
  517. ┴DDRESS:49 ═ARGARET ╙., 
  518.   ╫ATERLOO, ╧NT.
  519. ┬ORN ON ╬OV 6,1934
  520.  
  521.  
  522. ╒╬╔╧╬╙ -
  523.  
  524. ╘HERE IS ANOTHER MODE OF STORING 
  525. GROUPS OF VARIABLES IN ├ BESIDES 
  526. ARRAYS AND STRUCTURES AND IT'S CALLED 
  527. A ╒╬╔╧╬.
  528.  
  529. ┴ UNION DECLARATION ESTABLISHES A 
  530. SMALL SEGMENT OF MEMORY WHICH 
  531. CONTAINS ╧╬╠┘ ╧╬┼ VARIABLE AT A TIME 
  532. OUT OF A SET OF DIFFERENT VARIABLES.
  533.  
  534. ╔N MOST RESPECTS YOU CAN TREAT A 
  535. UNION IN THE SAME WAY THAT YOU TREAT 
  536. A STRUCTURE AS LONG AS YOU REMEMBER 
  537. THAT IT IS A STRUCTURE WHICH CAN 
  538. CONTAIN MANY DIFFERENT VARIABLE TYPES 
  539. ALL AT THE SAME TIME WHILE THE UNION 
  540. CAN ONLY CONTAIN ONE VARIABLE OUT OF 
  541. ITS SET OF DIFFERENT VARIABLES.
  542.  
  543. ┴ UNION LOOKS JUST LIKE A STRUCTURE:
  544.  
  545. UNION NAME.TAG █
  546.   CHAR C;
  547.   INT I;
  548.   FLOAT *F;
  549.   DOUBLE D;
  550. ▌ WHATEVER;
  551.  
  552. ╔N THE ABOVE WE HAVE DECLARED A UNION 
  553. WHICH HOLDS FOUR DIFFERENT VARIABLES 
  554. AND WE HAVE GIVEN IT THE TAG 
  555. 'NAME.TAG' AND WE HAVE CREATED A 
  556. PARTICULAR UNION CALLED 'WHATEVER'. 
  557. ╫HEN THE COMPILER SEES THIS 
  558. DECLARATION IT WILL RESERVE ENOUGH 
  559. MEMORY TO HOLD THE BIGGEST OF THE 
  560. VARIABLES IN THE UNION. ╔N THE CASE 
  561. OF ├ ╨OWER ON THE ├64 THIS WOULD BE 
  562. THE DOUBLE D, WHICH REQUIRES 5 BYTES 
  563. OF STORAGE. ┬Y RESERVING 5 BYTES FOR 
  564. THE UNION WHATEVER THE COMPILER 
  565. GUARANTEES THAT NO MATTER WHICH OF 
  566. THE FOUR VARIABLES IS PLACED IN THE 
  567. UNION AT ANY ONE TIME THERE WILL BE 
  568. ENOUGH SPACE FOR IT.
  569.  
  570. ╔F WE WANT TO CREATE ANOTHER UNION 
  571. JUST LIKE THE ONE ABOVE WE NOW ONLY
  572. HAVE NEED TO MAKE THIS DECLARATION:
  573.  
  574. UNION NAME.TAG SOMETHINGELSE;
  575.  
  576. ╧NE IMPORTANT THING TO KEEP IN MIND 
  577. WITH UNIONS IS THAT IT IS UP TO THE 
  578. PROGRAMMER TO KEEP TRACK OF WHAT IS 
  579. IN THE UNION. ╔F YOU PUT DOUBLE D 
  580. INTO THE UNION AND THEN TRY TO PULL 
  581. OUT INT I THE PROGRAM WILL PULL OUT 
  582. TWO BYTES OF THE DOUBLE AND YOU WILL 
  583. GET A GARBAGE VALUE.
  584. ╔F YOU NEED SOME WAY TO FIND OUT WHAT 
  585. TYPE OF VARIABLE IS IN THE UNION YOU 
  586. CAN USE THE ╙╔┌┼╧╞ OPERATOR TO TELL 
  587. YOU THE SIZE OF THE UNKNOWN VARIABLE. 
  588. ╔T WOULD BE USED SOMETHING LIKE THIS:
  589.  
  590. INT Y;
  591. Y = SIZEOF(WHATEVER);
  592.  
  593. ...AND Y WOULD BE EQUAL TO 5 IF THE 
  594. UNION CONTAINED A DOUBLE WHEN IT WAS 
  595. TESTED SINCE A DOUBLE TAKES 5 BYTES 
  596. OF STORAGE.
  597.  
  598.  
  599.  
  600. ╨╧╔╬╘┼╥╙ TO ╙╘╥╒├╘╒╥┼╙ -
  601.  
  602. ╧NE SOMETIMES FEELS FRUSTRATED IN 
  603. WRITING AN ELABORATE FUNCTION WHICH 
  604. DOES THE MOST WONDERFUL THINGS, ONLY 
  605. TO GET FROM SUCH A FUNCTION A SINGLE 
  606. INT OR FLOAT OR CHAR. ╥EMEMBER, YOU 
  607. CAN'T RETURN(A,B,C,D,E) AT THE END OF 
  608. THE FUNCTION, YOU CAN ONLY RETURN(A). 
  609.  
  610. ┬╒╘, THE FUNCTION CAN CREATE AN 
  611. ELABORATE STRUCTURE WHICH HOUSES ALL 
  612. THE WONDERFUL THINGS, THEN RETURN(A) 
  613. WHERE A IS A POINTER TO THE 
  614. STRUCTURE! 
  615.  
  616. ╔N FACT WE'VE USED SUCH A FUNCTION 
  617. ...ONE WHICH RETURNS A POINTER. 
  618. ┬EFORE ╔ TELL YOU WHICH FUNCTION IT 
  619. IS (FROM THE STDIO.H LIBRARY), LET'S 
  620. SEE HOW SUCH A FUNCTION SHOULD BE 
  621. DECLARED. 
  622.  
  623. ├ONSIDER THE FOLLOWING:
  624.  
  625. CHAR F();  WHICH DECLARES F() TO BE A 
  626. FUNCTION WHICH RETURNS A CHAR ╘HEN, 
  627. TO DECLARE A FUNCTION WHICH RETURNS A 
  628. POINTER TO A CHAR IT WOULD BE 
  629. SENSIBLE TO USE THE FORMAT: CHAR 
  630. *F();  ...RIGHT? 
  631. ╥╔╟╚╘! 
  632.  
  633. ╙╧ ...IF THE FUNCTION F() WERE TO 
  634. RETURN A POINTER TO A STRUCTURE 
  635. CALLED SAM, WE'D DECLARE IT WITH: 
  636.  
  637. SAM *F();
  638.  
  639. ... RIGHT?
  640.  
  641. ╥╔╟╚╘!
  642.  
  643. ┴ND WHAT IF SAM WAS TYPEDEFINED TO BE 
  644. A STRUCTURE, AS IN: 
  645.  
  646. TYPEDEF ╙OME╙TRUCTURE  ╙┴═;  
  647. /* REMEMBER THE USE OF CAPITALS! */
  648.  
  649. ╘HEN THE FUNCTION F() WOULD BE 
  650. DECLARED: 
  651.  
  652. ╙┴═ *F();... RIGHT?
  653.  
  654. ╬╧╫ ...REMEMBER WHEN WE USED:
  655.  
  656. ╞╔╠┼ *FOPEN(); ???
  657.  
  658. ╔N FACT, WHEN WE FOPEN() A FILE ON A 
  659. DISK, THE OPERATING SYSTEM RETURNS A 
  660. POINTER TO A STRUCTURE ( CALLED ╞╔╠┼ 
  661. ) AND THIS STRUCTURE CONTAINS ALL THE 
  662. WONDERFUL THINGS WE NEED TO KNOW 
  663. ABOUT THE FILE ...AND THAT'S WHY WE 
  664. ALSO DECLARE THIS POINTER FP: 
  665.  
  666. ╞╔╠┼ *FP, *FOPEN();
  667.  
  668. ...AND SAY, SUBSEQUENT TO THE ABOVE 
  669. DECLARATION: 
  670.  
  671.  FP=FOPEN();
  672.  
  673. ...SO WE ASSIGN TO FP THE POINTER 
  674. RETURNED BY FOPEN(). 
  675.  
  676. ╘HEN, WHEN WE WANT TO GET A CHARACTER 
  677. FROM THIS FILE, WE NEED ONLY PASS TO 
  678. GETC() THIS POINTER ( AS IN GETC(FP) 
  679. ) AND NOW THE GETC() FUNCTION WILL BE 
  680. ABLE TO EXTRACT ALL THE WONDERFUL 
  681. THINGS IT NEEDS FROM THE STRUCTURE 
  682. ╞╔╠┼. 
  683.  
  684.  
  685. ╬╧╫, IF SAM *F(); IS THE WAY WE 
  686. DECLARE F() TO BE A ╞╒╬├╘╔╧╬ ╫╚╔├╚ 
  687. ╥┼╘╒╥╬╙ ┴ ╨╧╔╬╘┼╥ TO AN OBJECT OF 
  688. ╘┘╨┼ SAM (WHICH COULD BE AN INT OR A 
  689. FLOAT OR A STRUCT ETC.), THEN HOW 
  690. SHOULD WE DECLARE F TO BE A ╨╧╔╬╘┼╥ 
  691. ╘╧ ┴ ╞╒╬├╘╔╧╬ ╫╚╔├╚ ╥┼╘╒╥╬╙ ┴╬ ╧┬╩┼├╘ 
  692. OF ╘┘╨┼ SAM? ╔T WOULD BE: 
  693.  
  694. SAM  (*F)();  
  695.  
  696. ...SAYS THAT F IS NOW THE POINTER 
  697. ...BECAUSE WE USED (*F) ...AND IF WE 
  698. WANT TO ACCESS THE THING WHICH F 
  699. POINTS TO WE WOULD USE THE TECHNIQUE 
  700. OF ╔╬─╔╥┼├╘╔╧╬ (GO BACK AND REVIEW IF 
  701. YOU DON'T REMEMBER!). ╘HE THING IT 
  702. POINTS TO ╔╙ *F ( REMEMBER THAT INT 
  703. *X; DECLARES X TO BE A POINTER TO AN 
  704. INT, AND THE INT ╔╙ *X ) 
  705.  
  706. ╙╧, SINCE (*F) IS TO BE A FUNCTION, 
  707. WE SAY (*F)() ! 
  708.  
  709. ...AND WE'VE SEEN THIS CURIOUS 
  710. NOTATION BEFORE TOO! 
  711.  
  712. ╙UPPOSE THAT PTR IS A POINTER TO A 
  713. STRUCTURE, DECLARED USING *PTR SO 
  714. THAT (*PTR) ╔╙ THE STRUCTURE ITSELF. 
  715. ╙UPPOSE THE STRUCTURE HAD A MEMBER 
  716. CALLED 'NAME'. ╘HEN WE'D REFER TO 
  717. THIS MEMBER AS:  
  718.  
  719. (*PTR).NAME
  720.  
  721. ...AS IN (*PTR).NAME="╟EORGE"; WHICH
  722. ASSIGNS '╟EORGE' TO THE VARIABLE
  723. 'NAME' IN WHATEVER STRUCTURE IT IS
  724. THAT PTR POINTS TO.
  725.  
  726. ┴NOTHER (SIMPLER) NOTATION FOR THE 
  727. SAME THING IS: 
  728.  
  729. PTR -> NAME = "╟EORGE";
  730. /* USE ONLY IF PTR IS A POINTER */
  731.  
  732. ...AND IF THE STRUCTURE HAD A MEMBER 
  733. BIRTH WHICH WAS ITSELF A STRUCTURE 
  734. CONTAINING A MEMBER CALLED MONTH, 
  735. THEN WE CAN USE THE NOTATION: 
  736.  
  737. PTR -> BIRTH.MONTH;
  738. /* WHICH MEANS (*PTR).BIRTH.MONTH */
  739.  
  740. ...AS IN PTR->BIRTH.MONTH="═AY";
  741.  
  742. ┴╬─, IF BIRTH HAPPENED TO BE A 
  743. POINTER TOO, WE'D USE: 
  744.  
  745. PTR -> BIRTH -> MONTH
  746.  
  747. ╥EMEMBER:
  748.  
  749. ╒SE:   SAM.BIRTH  
  750. IF SAM IS A STRUCTURE.
  751.  
  752. ╒SE:   SAM->BIRTH 
  753. IF SAM IS A POINTER TO A STRUCTURE.
  754.  
  755.  
  756.  
  757. ╨OINTERS TO ╒NIONS -
  758.  
  759. ╒NIONS CAN ALSO HAVE POINTERS TO THEM 
  760. VERY MUCH LIKE STRUCTURES DO.
  761. ╞OR EXAMPLE, IF YOU KNOW THAT THE 
  762. UNION WHATEVER (WHICH WE DECLARED 
  763. ABOVE) CONTAINS A DOUBLE AND YOU 
  764. WANTED TO ASSIGN THAT DOUBLE TO 
  765. ANOTHER DOUBLE VARIABLE CALLED, SAY, 
  766. D.ANSWER YOU COULD USE A POINTER AND 
  767. IN THIS CASE THE POINTER IS CALLED 
  768. U.PTR:
  769.  
  770. DOUBLE D.ANSWER; /* DECLARE DOUBLE */
  771. UNION NAME.TAG █
  772.   CHAR C;
  773.   INT I;
  774.   FLOAT *F;
  775.   DOUBLE D;
  776. ▌ WHATEVER;      /* DECLARE UNION */
  777. UNION NAME.TAG *U.PTR;
  778. /* DECLARE A POINTER TO UNION */
  779.  
  780. U.PTR = WHATEVER; /* POINT IT */
  781. WHATEVER = D; /* DOUBLE IN UNION */
  782. D.ANSWER = U.PTR -> D;
  783. /* D.ANSWER NOW CONTAINS THE VALUE
  784.    OF D */
  785.  
  786.  
  787. [┼ND OF PART 11 OF 11]
  788.