Commit | Line | Data |
---|---|---|
aedb329b | 1 | #ifndef lint |
0f4556f1 | 2 | static char sccsid[] = "@(#)selunit.c 4.2 (Berkeley) 4/25/83"; |
aedb329b KM |
3 | #endif not lint |
4 | ||
5 | #include "stdio.h" | |
6 | #include "lrnref.h" | |
7 | ||
8 | int nsave = 0; | |
2b9e3de9 | 9 | int review = 0; |
aedb329b KM |
10 | |
11 | selunit() | |
12 | { | |
aedb329b | 13 | static char dobuff[50]; |
2b9e3de9 KM |
14 | static char saved[20]; |
15 | char fnam[80], s[80], zb[200]; | |
aedb329b KM |
16 | char posslev[20][20]; |
17 | int diff[20], i, k, m, n, best, alts; | |
2b9e3de9 | 18 | char *getlesson(); |
aedb329b | 19 | FILE *f; |
aedb329b | 20 | |
2b9e3de9 KM |
21 | if (again) { |
22 | again = 0; | |
23 | if (todo=getlesson()) { | |
24 | if (!review) | |
25 | unsetdid(todo); | |
26 | return; | |
27 | } | |
28 | wrapup(1); | |
29 | } | |
aedb329b KM |
30 | while (ask) { |
31 | printf("What lesson? "); | |
32 | fflush(stdout); | |
33 | gets(dobuff); | |
34 | if (strcmp(dobuff, "bye") == 0) | |
2b9e3de9 KM |
35 | wrapup(1); |
36 | level = dobuff; | |
37 | if (todo=getlesson()) | |
aedb329b | 38 | return; |
aedb329b KM |
39 | } |
40 | alts = 0; | |
41 | retry: | |
2b9e3de9 | 42 | f = scrin; /* use old lesson to find next */ |
aedb329b | 43 | if (f==NULL) { |
2b9e3de9 | 44 | sprintf(fnam, "%s/%s/L%s", direct, sname, level); |
aedb329b KM |
45 | f = fopen(fnam, "r"); |
46 | if (f==NULL) { | |
2b9e3de9 KM |
47 | perror(fnam); |
48 | fprintf(stderr, "Selunit: no script for lesson %s.\n", level); | |
aedb329b KM |
49 | wrapup(1); |
50 | } | |
51 | while (fgets(zb, 200, f)) { | |
52 | trim(zb); | |
53 | if (strcmp(zb, "#next")==0) | |
54 | break; | |
55 | } | |
56 | } | |
57 | if (feof(f)) { | |
58 | printf("Congratulations; you have finished this sequence.\n"); | |
59 | fflush(stdout); | |
60 | todo = 0; | |
61 | return; | |
62 | } | |
2b9e3de9 | 63 | for(i=0; fgets(s, 80, f); i++) { |
aedb329b KM |
64 | sscanf(s, "%s %d", posslev[i], &diff[i]); |
65 | } | |
66 | best = -1; | |
67 | /* cycle through lessons from random start */ | |
68 | /* first try the current place, failing that back up to | |
69 | last place there are untried alternatives (but only one backup) */ | |
70 | n = grand()%i; | |
71 | for(k=0; k<i; k++) { | |
72 | m = (n+k)%i; | |
2b9e3de9 KM |
73 | if (already(posslev[m])) |
74 | continue; | |
75 | if (best<0) | |
76 | best = m; | |
77 | alts++; /* real alternatives */ | |
aedb329b | 78 | if (abs(diff[m]-speed) < abs(diff[best]-speed)) |
2b9e3de9 | 79 | best = m; |
aedb329b KM |
80 | } |
81 | if (best < 0 && nsave) { | |
82 | nsave--; | |
83 | strcpy(level, saved); | |
84 | goto retry; | |
85 | } | |
2b9e3de9 | 86 | if (best < 0) { |
aedb329b KM |
87 | /* lessons exhausted or missing */ |
88 | printf("Sorry, there are no alternative lessons at this stage.\n"); | |
89 | printf("See someone for help.\n"); | |
90 | fflush(stdout); | |
91 | todo = 0; | |
92 | return; | |
93 | } | |
94 | strcpy (dobuff, posslev[best]); | |
95 | if (alts>1) { | |
2b9e3de9 KM |
96 | nsave = 1; |
97 | strcpy(saved, level); | |
aedb329b KM |
98 | } |
99 | todo = dobuff; | |
100 | fclose(f); | |
101 | } | |
102 | ||
103 | abs(x) | |
104 | { | |
2b9e3de9 | 105 | return(x>=0 ? x : -x); |
aedb329b KM |
106 | } |
107 | ||
108 | grand() | |
109 | { | |
110 | static int garbage; | |
111 | int a[2], b; | |
112 | ||
113 | time(a); | |
114 | b = a[1]+10*garbage++; | |
115 | return(b&077777); | |
116 | } |