1implement Polyhedra; 2 3include "sys.m"; 4 sys: Sys; 5include "bufio.m"; 6 bufio: Bufio; 7 Iobuf: import bufio; 8include "math/polyhedra.m"; 9 10scanpolyhedra(f: string): (int, ref Polyhedron, ref Iobuf) 11{ 12 first, last: ref Polyhedron; 13 D: int; 14 15 if(sys == nil) 16 sys = load Sys Sys->PATH; 17 if(bufio == nil) 18 bufio = load Bufio Bufio->PATH; 19 b := bufio->open(f, Sys->OREAD); 20 if(b == nil) 21 return (0, nil, nil); 22 n := 0; 23 for(;;){ 24 s := getstring(b); 25 if(s == nil) 26 break; 27 n++; 28 p := ref Polyhedron; 29 if(first == nil) 30 first = p; 31 else{ 32 last.nxt = p; 33 p.prv = last; 34 } 35 last = p; 36 p.name = s; 37 p.dname = getstring(b); 38 b.gets('\n'); 39 (p.allf, p.adj) = scanvc(getstring(b)); 40 b.gets('\n'); 41 b.gets('\n'); 42 b.gets('\n'); 43 l := getstring(b); 44 (p.indx, l) = getint(l); 45 (p.V, l) = getint(l); 46 (p.E, l) = getint(l); 47 (p.F, l) = getint(l); 48 (nil, l) = getint(l); 49 (D, l) = getint(l); 50 (p.anti, l) = getint(l); 51 p.concave = D != 1 || p.allf; 52 p.offset = b.offset(); 53 tot := 2*p.V+2*p.F; 54 for(i := 0; i < tot; i++) 55 b.gets('\n'); 56 if(p.indx < 58 || p.indx == 59 || p.indx == 66 || p.indx == 67) 57 p.inc = 0.1; 58 else 59 p.inc = 0.0; 60 # sys->print("%d: %d %d %d %d %s\n", p.indx, p.allf, D != 1, p.anti, p.concave, vc); 61 } 62 first.prv = last; 63 last.nxt = first; 64 return (n, first, b); 65} 66 67getpolyhedra(p: ref Polyhedron, b: ref Iobuf) 68{ 69 q := p; 70 do{ 71 getpolyhedron(q, b); 72 q = q.nxt; 73 }while(q != p); 74} 75 76getpolyhedron(p: ref Polyhedron, b: ref Iobuf) 77{ 78 if(p.v != nil) 79 return; 80 b.seek(p.offset, Bufio->SEEKSTART); 81 p.v = array[p.V] of Vector; 82 for(i := 0; i < p.V; i++) 83 p.v[i] = getvector(b); 84 p.f = array[p.F] of Vector; 85 for(i = 0; i < p.F; i++) 86 p.f[i] = getvector(b); 87 p.fv = array[p.F] of array of int; 88 for(i = 0; i < p.F; i++) 89 p.fv[i] = getarray(b, p.adj); 90 p.vf = array[p.V] of array of int; 91 for(i = 0; i < p.V; i++) 92 p.vf[i] = getarray(b, p.adj); 93} 94 95getstring(b: ref Iobuf): string 96{ 97 s := b.gets('\n'); 98 if(s == nil) 99 return nil; 100 if(s[0] == '#') 101 return getstring(b); 102 if(s[len s - 1] == '\n') 103 return s[0: len s - 1]; 104 return s; 105} 106 107getvector(b: ref Iobuf): Vector 108{ 109 v: Vector; 110 111 s := getstring(b); 112 (v.x, s) = getreal(s); 113 (v.y, s) = getreal(s); 114 (v.z, s) = getreal(s); 115 return v; 116} 117 118getarray(b: ref Iobuf, adj: int): array of int 119{ 120 n, d: int; 121 122 s := getstring(b); 123 (n, s) = getint(s); 124 a := array[n+2] of int; 125 a[0] = n; 126 for(i := 1; i <= n; i++) 127 (a[i], s) = getint(s); 128 (d, s) = getint(s); 129 if(d == 0 || d == n-1 || adj) 130 d = 1; 131 a[n+1] = d; 132 return a; 133} 134 135getint(s: string): (int, string) 136{ 137 n := int s; 138 for(i := 0; i < len s && s[i] == ' '; i++) 139 ; 140 for( ; i < len s; i++) 141 if(s[i] == ' ') 142 return (n, s[i+1:]); 143 return (n, nil); 144} 145 146getreal(s: string): (real, string) 147{ 148 r := real s; 149 for(i := 0; i < len s && s[i] == ' '; i++) 150 ; 151 for( ; i < len s; i++) 152 if(s[i] == ' ') 153 return (r, s[i+1:]); 154 return (r, nil); 155} 156 157vftab := array[] of { 0, 0, 0, 2, 3, 3, 5, 0, 3, 0, 3 }; 158 159scanvc(s: string): (int, int) 160{ 161 af := 0; 162 ad := 0; 163 fd := ld := 1; 164 ln := len s; 165 if(ln > 0 && s[0] == '('){ 166 s = s[1:]; 167 ln--; 168 } 169 while(ln > 0 && s[ln-1] != ')'){ 170 s = s[0: ln-1]; 171 ln--; 172 } 173 (m, lst) := sys->tokenize(s, "."); 174 for(l := lst ; l != nil; l = tl l){ 175 (m, lst) = sys->tokenize(hd l, "/"); 176 if(m == 1) 177 (n, d) := (int hd lst, 1); 178 else if(m == 2) 179 (n, d) = (int hd lst, int hd tl lst); 180 else 181 sys->print("vc error\n"); 182 if(d != 1 && d == vftab[n]) 183 af = 1; 184 if(d == n-1) 185 d = 1; 186 if(l == lst) 187 fd = d; 188 else if(ld != 1 && d != 1) 189 ad = 1; 190 ld = d; 191 } 192 if(ld != 1 && fd != 1) 193 ad = 1; 194 return (af, ad); 195} 196