1 public class Berechner {
2 // macht die Arbeit, die eigentlich schon der Kollege bzw.
3 // die Kollegin vor uns hätte machen sollen. Schade, dass
4 // keines der beiden Beispiele brauchbar ist!
5 //
6
7
8 private final static String[] laengen_einheiten={"cm", "dm", "m"};
9 private final static String[] flaechen_einheiten={"cm2", "dm2", "m2"};
10 private final static String[] raum_einheiten={"cm3", "dm3", "m3"};
11
12 private final static String[] alle_einheiten={
13 "cm", "dm", "m", "cm2", "dm2", "m2", "cm3", "dm3", "m3" };
14
15 public Berechner() throws Exception {
16 }
17
18
19 private static boolean debugging=false;
20 public static void debug(String s) {
21 if(debugging)
22 System.out.println(s);
23 }
24
25
26 // getEinheit
27 // ..............................................................
28 // liefert den Einheitsteil zurück, wenn vorhanden.
29 // wirft Exception, falls String keine bzw. ungültige Einheit hat
30 //
31 public static String getEinheit(String s) throws Exception {
32 for(int i=0; i<3; i++) {
33 if(s.endsWith(laengen_einheiten[i]))
34 return(laengen_einheiten[i]);
35
36 if(s.endsWith(flaechen_einheiten[i]))
37 return(flaechen_einheiten[i]);
38
39 if(s.endsWith(raum_einheiten[i]))
40 return(raum_einheiten[i]);
41 }
42
43 throw(new Exception("String "+s+" enthält unbekannte Einheit!"));
44 }
45
46
47 // getDimension
48 // ..............................................................
49 // betrachtet die Einheit des übergebenen strings und liefert
50 // dessen dimension zurück. 1 für länge, 2 für fläche, 3 für raum
51 // wirft Exception, falls Dimension ungültig
52 //
53 // ACHTUNG!!! wenn die Einheit ungültig ist, ist auch das
54 // Ergebnis ungültig. Deshalb: Nur mit getEinheit
55 // verwenden!
56 //
57 public static int getDimension(String s) throws Exception {
58 if(s.endsWith("3"))
59 return(3);
60 else
61 if(s.endsWith("2"))
62 return(2);
63 else
64 if(s.endsWith("m"))
65 return(1);
66
67
68 throw(new Exception("Ungültige Dimension; weder "+
69 "Längen-, Flächen- noch Raummaß!"));
70 }
71
72
73 // isValidOperator
74 // ..............................................................
75 // liefert true, falls übergebener String +, -, *, /, ( oder )
76 // liefert false, wenn nicht
77 //
78 public static boolean isValidOperator(String s) {
79 if(s.length()!=1)
80 return(false);
81
82 final String operators="+-*/()";
83
84 for(int i=0; i
85 if(s.charAt(0)==operators.charAt(i))
86 return(true);
87
88 return(false);
89 }
90
91
92 public static boolean isNumeric(char c) {
93 return(c>='0' && c<='9');
94 }
95
96
97 // isValidWert
98 // .............................................................
99 // liefert true, wenn String von Bauart
100 // [.] ist.
101 //
102 // liefert false, wenn nicht.
103 //
104 // muß angegeben werden, rein numerisch
105 // . und KÖNNEN angegeben werden
106 // muß angegeben werden und eine der defi-
107 // nierten längen / flächen / raumeinheiten sein
108 //
109 public static boolean isValidWert(String s) {
110 int i=0;
111
112 if(s.length()<2 || !isNumeric(s.charAt(0)))
113 return(false);
114
115 while(i
116 i++;
117
118 if(s.charAt(i) == '.') { // Nachkommaanteil ?
119 i++;
120
121 if(!isNumeric(s.charAt(i)))
122 return(false);
123
124 while(i
125 i++;
126 }
127
128 try {
129 debug("prüfe, ob "+s.substring(i)+" in "+
130 arrToString(alle_einheiten,9));
131 posInStringArray(s.substring(i), alle_einheiten, 9);
132 debug(" --> ja");
133 return(true);
134 } catch(Exception e) {
135 debug(" --> nein");
136 return(false);
137 }
138 }
139
140
141 // getWert
142 // .............................................................
143 // liefert den numerischen Anteil des Wertes des übergebenen
144 // Strings.
145 //
146 // ACHTUNG!! Ich verlasse mich hier wiedermal darauf, dass der
147 // übergebene String gültig ist. Wenn nicht: Böses
148 // Erwachen!!
149 //
150 public static String getWertNumeric(String s) {
151 int i=0;
152
153 while(i
154 i++;
155
156 if(s.charAt(i) == '.') {
157 i++;
158
159 while(i
160 i++;
161 }
162
163 return(s.substring(0,i));
164 }
165
166 // arrToString
167 // ................................................................
168 // Wandelt für Exceptions & Co ein Stringarray in einen String
169 //
170 public static String arrToString(String[] arr, int arr_size)
171 throws Exception {
172
173 if(arr_size<=0)
174 return("[]");
175
176 if(arr_size==1)
177 return("["+arr[0]+"]");
178
179 String s="[";
180
181 for(int i=0; i<(arr_size-1); i++)
182 s=s+arr[i]+",";
183
184 return(s+arr[arr_size-1]+"]");
185 }
186
187
188 // posInStringArray
189 // ................................................................
190 // schaut nach, an welcher Stelle s im Array arr vorkommt. Wenn es
191 // gar nicht vorkommt --> Exception!
192 //
193 public static int posInStringArray(String s, String[] arr,
194 int arr_size) throws Exception {
195 int i=0;
196
197 while(i
198 if(arr[i].equals(s))
199 return(i);
200 else
201 i++;
202
203 throw(new Exception("String "+s+" in Array "+
204 arrToString(arr, arr_size)+
205 " nicht gefunden!"));
206 }
207
208
209
210 public static float normalisiere(String n, String e,
211 String[] einheiten, float faktor) throws Exception {
212
213 int i=posInStringArray(e, einheiten, 3);
214 float result=Float.parseFloat(n);
215
216 debug("normalisiere("+n+","+e+","+arrToString(einheiten, 3)+"...);");
217
218 while(i<2) {
219 result/=faktor;
220 i++;
221 }
222
223 return(result);
224 }
225
226
227
228 public static float normalisiere_laenge(String n, String e)
229 throws Exception {
230
231 return(normalisiere(n, e, laengen_einheiten,
232 (float)10.0));
233 }
234
235
236 public static float normalisiere_flaeche(String n, String e)
237 throws Exception {
238
239 return(normalisiere(n, e, flaechen_einheiten,
240 (float)100.0));
241 }
242
243
244 public static float normalisiere_raum(String n, String e)
245 throws Exception {
246
247 return(normalisiere(n, e, raum_einheiten,
248 (float)1000.0));
249
250 }
251
252
253 // calcWertFloat
254 // ............................................................
255 // wandelt den Wert-String und Einheits-String in eine auf
256 // Meter normalisierte Float-Zahl um.
257 //
258 public static float convertWertToFloat(String numerischer_anteil,
259 String einheits_anteil) throws Exception {
260
261 switch(getDimension(einheits_anteil)) {
262
263 case 1: return(normalisiere_laenge(
264 numerischer_anteil,
265 einheits_anteil));
266
267 case 2: return(normalisiere_flaeche(
268 numerischer_anteil,
269 einheits_anteil));
270
271 case 3: return(normalisiere_raum(
272 numerischer_anteil,
273 einheits_anteil));
274 }
275
276 throw(new Exception("Einheit "+einheits_anteil+" hat"+
277 "unerwartete Dimension!"));
278 }
279
280
281 public static String normalisierteEinheit(int dimension)
282 throws Exception {
283
284 switch(dimension) {
285 case 1: return("m");
286 case 2: return("m2");
287 case 3: return("m3");
288 }
289
290 throw(new Exception("Dimension "+dimension+
291 " ungültig!"));
292 }
293
294
295 public static String normalisiereWert(String wert) {
296 if(wert.indexOf('.') == -1)
297 wert=wert+'.';
298
299 while((wert.length() - wert.indexOf('.')) <= 3)
300 wert=wert+'0';
301
302 return(wert);
303 }
304
305 public static String normalisiereWert(float f) {
306 return(normalisiereWert(Float.toString(f)));
307 }
308
309
310 public static String addiere(String a, String b)
311 throws Exception {
312
313 int ad=getDimension(a), bd=getDimension(b);
314 String ae=getEinheit(a), be=getEinheit(b);
315
316 if(ad!=bd)
317 throw(new Exception(a+" und "+b+" sind von "+
318 "unterschiedlicher Dimension!"));
319
320 float ergebnis=convertWertToFloat(getWertNumeric(a),ae)+
321 convertWertToFloat(getWertNumeric(b),be);
322
323 return( normalisiereWert(ergebnis) +
324 normalisierteEinheit(ad));
325 }
326
327
328 public static String subtrahiere(String a, String b)
329 throws Exception {
330
331 int ad=getDimension(a), bd=getDimension(b);
332 String ae=getEinheit(a), be=getEinheit(b);
333
334 if(ad!=bd)
335 throw(new Exception(a+" und "+b+" sind von "+
336 "unterschiedlicher Dimension!"));
337
338 float ergebnis=convertWertToFloat(getWertNumeric(a),ae)-
339 convertWertToFloat(getWertNumeric(b),be);
340
341 return( normalisiereWert(ergebnis) +
342 normalisierteEinheit(ad) );
343 }
344
345
346 public static String multipliziere(String a, String b)
347 throws Exception {
348
349 int ad=getDimension(a), bd=getDimension(b);
350 String ae=getEinheit(a), be=getEinheit(b);
351
352 if((ad+bd)>3)
353 throw(new Exception("Multiplikation von "+a+
354 " und "+b+" würden eine zu hohe "+
355 "Dimension ergeben!"));
356
357 float ergebnis=convertWertToFloat(getWertNumeric(a),ae)*
358 convertWertToFloat(getWertNumeric(b),be);
359
360 return( normalisiereWert(ergebnis) +
361 normalisierteEinheit(ad+bd) );
362 }
363
364
365 public static String dividiere(String a, String b)
366 throws Exception {
367
368 int ad=getDimension(a), bd=getDimension(b);
369 String ae=getEinheit(a), be=getEinheit(b);
370 String an=getWertNumeric(a), bn=getWertNumeric(b);
371 float af=convertWertToFloat(an,ae),
372 bf=convertWertToFloat(bn,be);
373
374
375 if(bf==(float)0)
376 throw(new Exception("Division durch Null unzulässig!"));
377
378
379 if((ad-bd)<1)
380 throw(new Exception("Division von "+a+
381 " und "+b+" würden eine zu niedrige "+
382 "Dimension ergeben!"));
383
384
385 float ergebnis=af/bf;
386
387 return( normalisiereWert(ergebnis) +
388 normalisierteEinheit(ad-bd));
389 }
390
391
392 // berechne
393 // ............................................................
394 // ermittelt Ergebnis einer Operation
395 //
396 public static String berechne(String a, String op, String b)
397 throws Exception {
398
399 if(!isValidOperator(op))
400 throw(new Exception("Ungültiger Operator "+op));
401
402 if(!isValidWert(a) || !isValidWert(b))
403 throw(new Exception(a +" oder "+b+" ist ein"+
404 " ungültiger Wert!"));
405
406 String ae=getEinheit(a), be=getEinheit(b);
407 int ad=getDimension(a), bd=getDimension(b);
408
409 switch(op.charAt(0)) {
410 case '+': return(addiere(a,b));
411 case '-': return(subtrahiere(a,b));
412 case '*': return(multipliziere(a,b));
413 case '/': return(dividiere(a,b));
414 }
415
416 throw(new Exception("Unerwartete Operation "+op));
417 }
418 }
|