Deprecated: The each() function is deprecated. This message will be suppressed on further calls in /home/zhenxiangba/zhenxiangba.com/public_html/phproxy-improved-master/index.php on line 456
Opgaverne til denne gang indeholder (om muligt) endnu flere ting der kan gaa galt. Saa hvis du sidder fast i noget, saa lad vaere med at bruge en masse tid paa det! Lav hellere en posting paa nyhedsgruppen, og proev at komme videre. Hvis du sidder helt fast i LOCUM, saa gaa videre med JSpec-opgaverne. (0) LOCUM LOCUM (Langage à Objets en C Ultimement Moche) er en slags projektion af et simpelt OO sprog ned paa C. Der er klasser og objekter, og man kan lave virtuelle kald. Men man skal selv saette det hele sammen (man kunne lave en "Java2LOCUM", men det har jeg ikke haft tid til :-). Filen "point.h" er et eksempel paa hvordan man definerer en klasse. Foerst erklaeres objektet, derefter erklares dets vtable som skal indeholde en pointer til klassen, pointere til metoderne erklaeret i superklassen, og endelig de metoderne fra den lokale klasse. (Sammenlign med ObjectVTable fra "locum.h".) Desuden erklaeres det objekt der indeholder klassen, og den struktur der indeholder objektets vtable. Endelig er der en funktion der initialiserer klassen, og som man skal huske at kalde foer man bruger den foerste gang. Filen "point.c" erklarer blot de faktiske strukturer, og inkluderer en seperat fil hvor metoderne er erklaerede. Der er for eksempel en "equals" metode der teste om et andet objekt er et point og hvis saa om koordinaterne er de samme. Der er ogsaa en "toString" og et par metode til at tilgaa tilstanden. Endelig er der "init_Point" der stopper de rigtige metoder ind i klassens vtable. (Bemaerk at f.eks. metoden "Object_getClass" er nedarvet.) Filen "format.c" indeholder en formatterings-funktion, og "test.c" laver en lille test at den. For at compile test-programmet: gcc -Wall locum.c locum_lib.c test.c point.c format.c -o test Proev at koere det, og at forstaa hvad der foregaar paa runtime. (Brug evt. gdb til dynamisk at foelge med i udfoerslen af programmet.) Format eksemplet er klargjort til at kunne blive specialiseret med Tempo (ved at bruge filen "format.c"). Faa det til at specialisere, kig paa hvad der kommer af warnings (saa du ved hvad der ikke goer noget) og kig paa resultatet. Forstaa hvad der skete. (1) Implementer power-eksemplet i LOCUM - se appendix for en Java version. Analyser det for en kontekst hvor den binaere operator er enten addition eller multiplikation. Faa det til at specialisere med statisk operator og dynamisk base-vaerdi. Pitfalls: - Der er mange ting der kan gaa galt, saa det er bedst at foelge den kode-stil der er i format-eksemplet. - "ERROR (AT2SPEC 41): function body must be a block": se point_methods.c (2) Gen-analyser (1) med dynamisk operator og statisk base-vaerdi. Faa det til at specialisere. (3) Specialiser Java-versionen af power med JSpec. Lav f.eks. en fil "Pow.jspec" med foelgende indhold = module "Pow" = entry_point {int Power.raise(int base)} = entry_point_signature {S D} = main_classes {Power Binary Mul Add} = specialized_entry_point "raise_spec" = compile_during_weave 1 "Pow" bruges som basis-navn for f.eks. color-filerne. Entry point angives af to gange: da der jo er overloading paa metoder skal man angive hele signaturen. Bindingstiden angives i "entry_point_signature" som ogsaa angiver bindings-tiden af "this" objektet. "main_classes" angiver de klasser der skal specialiseres fra/til. (Den sidste switch faar JSpec til at gencompile Java-programmet med den specialiserede kode.) For at taende for inlining kan man bruge: = inlining 1 men bemaerk at det kun virker hvis alle fields er public. Lav saa en fil "_JSpec_Context" i stil med foelgende: import fr.irisa.compose.jspec.StaticValue; import fr.irisa.compose.jspec.DynamicValue; public class _JSpec_Context { public static Power _this; public static int base; // main metoden skal kalde main i en klasse der koerer programmet public static void main( String argv[] ) { Main.main( argv ); } public static void setAnalysisContext() { BinOp bin = StaticValue.get_boolean()?(BinOp)new Add():(BinOp)new Mul(); _this = new Power(bin,StaticValue.get_int()); base = DynamicValue.get_int(); } public static void setSpecializationContext() { _this = new Power(new Mul(),3); } } De to fields "_this" og "base" svarer til parametrene til entrypoint. De _skal_ have de samme navne som dem der blev angivet med "entry_point". For at compile _JSpec_Context.java skal der bruges en Main.java der bruger all de klasser der er relevante for specialiseringen, f.eks.: public class Main { public static void main(String argv[]) { System.out.println(new Power(new Mul(),(new Power(new Add(),2)).raise(3)).raise(4)); } } Slet derefter alle .class filer (JSpec bruger den aeldgamle JDK 1.0 som ikke kan lide de nyeste Java-compilere.), og koer: ~ups/JSpec/jspec/bin/jspec -javac Derefter skal det oversaettes til C kode, brug: ~ups/JSpec/jspec/bin/jspec -preprocess Pow (Hvis du overskrider din disk-kvota, saa faa en stoere en :-) Bemaerk at config.sml ogsaa bliver genereret paa nuvaerende tidspunkt, saa hvis du vil aendre i options i Pow.jspec, saa er du noedt til at starte forfra herfra igen. Alternativt kan du rette direkte i den genererede fil For at analysere programmet, brug ~ups/JSpec/jspec/bin/jspec -analyze Pow Det tager et paent stykke tid (f.eks. 10 minutter - saa er du advaret!) Hvis alt gaar vel, saa specialiser ~ups/JSpec/jspec/bin/jspec -specialize Pow Det tager ogsaa noget laengere tid end du er vant til, men ikke saa lang tid som at analysere. Hvis der opstaar et problem undervejs, saa kig hurtigt paa om du kan overskue hvad der gik galt, ellers lav en posting paa nyhedsgruppen. Alle filerne ligger i det subdirectory der hedder "jwd". Kig gerne paa f.eks. bta.color eller at.color filerne for at se hvad der sker. Men koncentrer dig om de relevante funktioner - der er virkelig meget "stoej" i filerne. (4) Som (2), bare med programmet fra (3). (5) Genimplementer format-eksemplet fra (1) i Java, og specialiser det med JSpec. Husk: jo mindre fancy, jo stoerre er chancen for at det kommer igennem. F.eks. er det en daarlig ide at bruge avancerede operatorer saasom "+="... -------------------------------------------------------------------------------- APPENDIX: power i Java -------------------------------------------------------------------------------- public abstract class BinOp { public abstract int apply(int x, int y); public abstract int neutral(); } public class Mul extends BinOp { public int apply(int x, int y) { return x*y; } public int neutral() { return 1; } } public class Add extends BinOp { ... } public class Power { BinOp op; int exp; public Power(BinOp op, int exp) { this.op=op; this.exp=exp; } public int raise(int base) { int r=op.neutral(); int e=this.exp; while(e-->0) r=op.apply(r,base); return r; } } --------------------------------------------------------------------------------