ZeptoN正在将程序放入Java
1.簡介
Java編程語言或“ Java”于1995年引入。然而,在近25年的時間里,它增加了最初不是核心語言所具有的功能。 此類功能包括枚舉,泛型,對基本C樣式功能開關語句的許多增強,斷言等。 Java是一種編程語言,隨著時間的發展,可以滿足Java軟件開發人員的需求。 請注意,在運行時以及支持庫,程序包,工具和實用程序等Java環境中,也添加和刪除了元素(分別為Java shell和Java applet。),但是這里的重點是Java,即編程語言。
Java的成功和流行使得它被用來教授編碼。 計算機科學AP(高級分班)考試使用Java。 Java的問題是一個悖論。 隨著Java的成功以及許多開發人員編寫Java代碼,那些對編程不熟悉的人和那些試圖學習編程的人都被遺忘了。
2.問題是編程中沒有程序
曾經在1980年代和1990年代有抱負的開發人員開始學習使用無處不在的BASIC進行編碼,然后轉移到Pascal(或FORTRAN,C),然后轉移到功能更強大的面向對象的語言,例如Objective-C,C ++,Smalltalk,Java 。 在此過程中,過渡是從基本編程概念(例如變量與常量,輸入或輸出,if語句等)在對象,類上進行的,然后到面向對象的原理和設計模式的過渡。軟件開發人員的路徑。
但是,學習Java的新手或“新手”必須應對眾多功能,這些功能要么被忽略,要么在使用時卻不知道該功能的用途。 這是“不關注窗簾背后的人”(綠野仙蹤)。 或Java的外來功能是又一個增加認知超負荷的功能。 也就是說,“……教師同時向學習者提供太多信息或太多任務,導致學習者無法處理此信息的情況。” [Brit 2019]這是一個神話,在這個神話中,新手無奈地將計算機扔到了窗外,然后失去了學習編碼的興趣。
3.計劃實體
因此,Java編程缺少程序實體來簡單地編寫應用程序或程序。 諸如BASIC和Pascal之類的較早的結構化編程語言不過是程序實體。 因此,對于Java的復雜性,優雅性和強大的功能,它缺少所有程序中最簡單的功能。 考慮下面的經典程序,但使用BASIC的簡單程序,以讀取用戶名,然后打印問候語。 [Wiki 2019a] BASIC源代碼為:
10 PRINT "what is your name?" 20 INPUT "...(Enter Your Name)...", a$ 30 PRINT 40 PRINT "hello, "; a$; ", I am your computer, nice to meet you." 60 ENDJava源代碼中相同的BASIC程序是:
import java.util.Scanner; class WhatIsYourName {private WhatIsYourName(){}public static void main(String[] args){System.out.println("what is your name?");System.out.print("...(Enter Your Name)..."); String name = System.console().readLine();System.out.printf("hello, %s, I am your computer, nice to meet you.%n", name);System.exit(0); }//end main;}//end class WhatIsYourName相比之下,兩種編程語言都可以達到與程序相同的最終結果,讀取用戶名,然后向他們打印問候語。 但是,Java版本需要公開一些需要進一步理解或忽略的細節。 考慮一下新手會問有關Java代碼的一些可能的問題:
4.一切面向對象
使用Java的這種基本,簡單的程序應用程序需要許多面向對象的功能。 再舉一個例子,考慮簡單而臭名昭著的“ Hello,World !!!” 在BASIC與Java中。
4.1使用Zepton編程為Java
該說明性示例說明了對程序實體構造的需求。 與類相似,不同之處在于程序是執行或應用程序的單元,而不是可重用的對象。 一個示例是相同的BASIC程序,但是用ZeptoN表示為程序而不是Java類:
prog WhatIsYourName { beginprintln("what is your name?");print("...(Enter Your Name)..."); String name = readLine();printf("hello, %s, I am your computer, nice to meet you.%n", name);exit(0);}//end prog WhatIsYourNameZeptoN程序更具可讀性,簡單性和緊湊性。 ZeptoN轉編譯器[Gilr 2019b]將ZeptoN程序轉換為Java類時,將自動創建必要的main(String [] args)方法,以及一些提供默認環境的“樣板”源代碼。
樣板源代碼只是包裝在公共靜態方法中的簡單方法調用。 因此,“ System.out.println(…)”就是具有相同參數類型簽名的“ println(…)”。 或者,“ System.exit(…)”也就是具有相同參數類型的“ exit(…)”。
所需的導入語句將自動生成。 總體而言,樣板源代碼中大約有70種方法和屬性。 一個重要的原則是ZeptoN的特定方法和屬性很少,并且方法名稱是相同的,并且具有相同的參數類型簽名。 因此,ZeptoN開發人員可以回到Java,或從Java遷移到ZeptoN,而不會遇到任何問題。
4.2 ZeptoN中的非標準方法
一種非標準靜態方法是“ String [] getArgs()”,該方法獲取命令行程序參數。 另一個是“ void nop()”,表示對存根方法沒有任何操作。 Java的語句為空,但是“ nop()”更為明確。 一些非標準常量是EMPTY_STRING,EMPTY_CHAR和NULL_CHAR。
再次將非標準方法和屬性保留為少數,以避免混淆的Java源代碼。 標準方法是“ String readLine()”,但不需要使用Java Scanner,BufferedReader或其他類。 ZeptoN強調簡潔性。 而且,作為ZeptoN的創建者,開發人員和第一個程序員,它總是使我很煩惱,String類沒有魔術常數EMPTY_STRING,而Character類沒有EMPTY_CHAR或NULL_CHAR。 我試圖保持邏輯,但我仍然……感到厭煩。 但是許多編程語言通常會根據他們的經驗而具有設計者的特質。
4.3 ZeptoN的摘要
ZeptoN是Java,但是它將程序實體從程序實體反編譯為一個類,轉換main()方法,并添加一組與其他類中的方法和屬性類似的樣板方法和屬性。 從而創建供開發人員使用的默認環境。 這很容易使用轉編譯器實現,從而避免了完整的Java編譯器實現的開銷和復雜性。 反編譯器將ZeptoN編譯為Java,然后使用Java Compiler API編譯為字節碼。
對于特定的JDK版本,ZeptoN“自動”具有這些功能。 因此,例如,如果使用JDK 13,則文本塊是ZeptoN中功能的一部分。 ZeptoN as Java包含Java的功能。 因此,對于Java的下一版本JDK 14,記錄可能是ZeptoN中的一項功能。
現在,由于ZeptoN是基本的反編譯器,因此可以擴展ZeptoN以添加其他功能,然后再將這些功能反編譯為Java。 目標是一致地添加這種功能,但也要避免完整的編譯器實現。 幸運的是,Java具有一組功能豐富的軟件包和類,這些軟件包和類可以通過一些工作和富有創意的思想來實現。
5.擴展ZeptoN
原始類型有時會在編寫Java以及擴展ZeptoN方面引起皺紋。 因此,該功能是在ZeptoN中將原始類型自動轉換為類包裝器類型。 從原始類型自動轉換為對象形式(我稱之為“提升為對象”)的這一功能可以使用轉編譯器輕松實現。 這些論點都主張使用原始類型支持[Moor 2014]和反對[Alpe 2000]。 最好的方法是讓開發人員在用ZeptoN編寫源代碼時有這種選擇。
5.1基本類型
Java語言規范Java SE 13版[Orac 2019]將原語類型定義為“原語類型由Java編程語言預定義并由其reserved關鍵字命名。” 更具描述性的定義是原始類型,它是Java編程語言中預定義的數據。 類型“ null”和“ void”不在原始類型中。
Null是默認引用值,或“ null類型具有一個值,null引用,由null文字null表示”。[Orac 2019] void類型指示非返回值方法,或“在方法聲明和定義中使用若要指定該方法不返回任何類型,則該方法返回void。 它不是一種類型,并且沒有C / C ++中的無效引用/指針。” [Wiki 2019b]
由于ZeptoN是Java,因此可以得出以下結論:基本類型完全相似。
5.2對象包裝器類型
基本類型是有效的,但是Java中的一個“皺紋”不是對象。 沒有引用原始類型,沒有任何對象或狀態。 但是對象類型有時是必要且有用的。 因此,Java提供了對象包裝器類型來使原語對象化。
Eckel [Ecke 2003]將對象類型包裝器描述為:“原始數據類型的“包裝器”類允許您在堆上創建一個非原始對象來表示該原始類型。”
例如,要將原始類型與任何Java集合一起使用,則需要將原始類型作為對象類型。 Java具有自動將原始類型提升為對象類型包裝器的功能。
5.3自動裝箱性能
具有自動裝箱的功能(因為ZeptoN中使用Java 5),但是更簡單的方法是簡單地將所有原始類型提升為對象。 Java在大多數原語之間使用自動裝箱(null和void除外),但是在原語類型(例如,簡單為datum)和包裝類型Integer(作為對象)之間沒有聯系。
另一個重要的考慮因素是性能,對自動裝箱的無限制使用和未考慮使用都可能導致Java字節碼出現性能問題。 升級為對象的此功能的最大優點之一是編寫的代碼更少,源代碼更干凈。
無效和無效這兩個原始類型不是基準,因此不會提升為對象。 布爾,字節,字符,雙精度型,浮點型,整型,長型和短型這8種原始類型被提升為對象。 但是與原始類型相比,對象類型將使用更多的內存。
5.4用原始類型轉譯ZeptoN源
考慮以下簡單的ZeptoN程序“ polyMathPrimitive1.zep”,該程序根據for循環(因此為多項式)中的索引來計算數字,但使用原始類型int進行計算。 靜態方法“ polyMathLoop”用作從程序塊調用的方法。
package javacodegeeks; prog polyMathPrimitive1 {static void polyMathLoop(final int loopLimit){for (int index = 0; index < loopLimit; index++) {int number = index * index * index + index * index + index; }//end for}//end polyMathLoopbeginlong timeStart = nanoTime();polyMathLoop(1000);long timeClose = nanoTime();printf("Total time: %d nanosec%n",(timeClose-timeStart)); println();exit(0); }使用整數常量1000調用polyMathLoop()方法。除了重復計算相同的多項式之外,該方法實際上不做任何事情。
使用ZeptoN編譯器進行編譯時,然后運行:
/Users/williamgilreath$java -cp . Zep polyMathPrimitive.zep /Users/williamgilreath$java -cp . javacodegeeks.polyMathPrimitive1 Total time: 18484 nanosecZeptoN程序“ polyMathObject.zep”說明了等效的ZeptoN在編譯時為:
package javacodegeeks; prog polyMathObject {static void polyMathLoop(final Integer loopLimit){for (Integer index = 0; index < loopLimit; index++) {Integer number = index * index * index + index * index + index; }//end for}//end polyMathLoopbeginlong timeStart = nanoTime();polyMathLoop(1000);long timeClose = nanoTime();printf("Total time: %d nanosec%n",(timeClose-timeStart)); println();exit(0);}使用ZeptoN編譯器進行編譯時,然后運行:
/Users/williamgilreath$java -cp . ZepC polyMathObject.zep /Users/williamgilreath$java -cp . javacodegeeks.polyMathObject Total time: 512084 nanosec兩個性能時間的比率表明總比率為1:27.7。 顯然,將每個原語完全升級為對象類型可能會對性能造成問題。
考慮一種替代方法,其中ZeptoN程序中并非每個整數都是原始int或對象包裝Integer。 ZeptoN源代碼為:
package javacodegeeks; prog polyMathPrimitive2 {static void polyMathLoop(final Integer loopLimit){ for (int index = 0; index < loopLimit; index++) {int number = index * index * index + index * index + index; }//end for}//end polyMathLoopbeginlong timeStart = nanoTime();polyMathLoop(1000);long timeClose = nanoTime();printf("Total time: %d nanosec%n",(timeClose-timeStart)); println();exit(0); }使用ZeptoN編譯器進行編譯時,然后運行:
/Users/williamgilreath$java -cp . Zep polyMathPrimitive2.zep /Users/williamgilreath$java -cp . javacodegeeks.polyMathPrimitive2 Total time: 92350 nanosec表演時間的比例表明總體比例為1:5的差異。 與純對象包裝類型實現相比,這是性能上的改進。 混合方法的性能更高。
5.5“促銷到對象”的功能語法
之前和之后的示例說明了從原始int到對象包裝的轉換Integer是全部或全部。 性能顯然會受到極大影響。 但是,在某些情況下,開發人員想要指定原始類型仍然是原始類型,尤其是在性能指標上。 這反映了前述方法的特點,即為開發人員提供了基本類型或對象類型的選擇。
語法是從原始類型升級為對象類型的一種排斥。 對于語法,沒有任何其他指示符的普通原語被提升為對象類型。 因此,int變成Integer,double變成Double,依此類推。
排除語法是從JavaCC [ref]語法中“借用”的,用于表達語法規則,正如Copeland [Cope 2009]解釋的那樣,“……是嗎? 量詞,它與指定模式的零個或一次匹配。”
從提升為對象類型中排除的原始類型具有字符“?”的結尾“鉤”或“問號”。 在標識符之后指示轉編譯器不要將原始類型提升為對象類型。 帶有“?”字符 原始類型仍然是原始類型。 因此是“ int?” 被編譯為“ int”而不是“ Integer”,因為沒有提升對象類型。
重寫原始類型和對象類型的原始混合語法,ZeptoN源代碼中的此語法為:
package javacodegeeks;prog polyMathSyntax {static void polyMathLoop(final int loopLimit){for (int? index = 0; index < loopLimit; index++) {int? number = index * index * index + index * index + index;}//end for}//end polyMathLoopbeginlong? timeStart = nanoTime();polyMathLoop(1000);long? timeClose = nanoTime();printf("Total time: %d nanosec%n",(timeClose-timeStart)); println();exit(0); }從語法重新編譯為通用Java源代碼后,“ polyMathSyntax.zep” ZeptoN程序等效于“ polyMathPrimitive2.zep” ZeptoN程序。
該語法允許開發人員選擇是將基元保留為基元類型,還是提升為對象類型包裝器。 因此,開發人員處于控制之中,而不是ZeptoN反編譯器。 語法有點熟悉,類似于JavaCC生產規則,Kotlin的語法用于允許的無效值,Swift的語法用于nil。 因此,盡管語義完全不同,但語法還是有些熟悉。
6.功能語法的Transpiler
指定原始類型的語法很簡單,很熟悉,仍然保持原始。 問題是如何在反編譯器中實現此功能,以便將ZeptoN反編譯為Java源代碼。 但是ZeptoN轉編譯器已經將ZeptoN源代碼轉換為Java源代碼,然后使用Java Compiler API對其進行編譯。
轉換功能語法的軟件實現面臨兩個挑戰:
這是經典的軟件開發工程師的任務-在現有的舊版軟件中實現功能。 簡而言之,創建一個新算法,然后在ZeptoN轉編譯器的舊版代碼中實現。
6.1特征算法
從基本類型到對象類型的特征的算法很簡單,與任何更復雜的編譯相比,它更具有正則表達式的搜索和替換過程。
該算法分為三個步驟:
算法的每個步驟然后依次處理下一步中的字符串,直到將具有語法功能的原始ZeptoN源轉換為具有原始類型和對象類型的ZeptoN源代碼。
6.1.1將原語重命名為中間標識符
該算法的第一步是保留要保留的基本體。 但是重命名是必需的,以避免搜索并替換為對象包裝器類型。 可以使用任何不同的替換,但是將原始字符的大寫字母與字母'Q'串聯在一起可以簡化要編寫的代碼,因為每個原始標識符都可以在搜索中使用,并可以用正則表達式替換。
6.1.2重命名原語為對象類型包裝器
中間步驟是在ZeptoN源代碼中搜索原始類型標識符并將其替換為對象類型標識符。 檢查并替換每個原始標識符。 因此,原語保持原語并在算法的最后一步中恢復。
6.1.3重命名中間標識符為原始類型
該算法的最后一步將還原已重命名的原始類型。 使用唯一的,不相同的標識符,將替換原始類型標識符而不會在末尾添加問號,并且在ZeptoN源代碼中,指示為在語法中保持原始的原始語言也是如此。
6.2功能語法的實現
該算法可以在一系列原始類型上使用三個for循環來實現,甚至可以更簡單地使用臭名昭著的“一個內襯”來實現,后者更像是使用一個for循環的流。 因此,使用原始類型來轉換ZeptoN源代碼字符串以提升并保留在基本ZeptoN源代碼中的Java源代碼就是“ transpileCode()”方法:
public static String transpileCode(final String zepCode){ String result = zepCode;final String[] primitiveList = new String[]{"boolean", "byte", "char", "double", "float", "int", "long", “short" };final String[] objectTypeList = new String[]{"Boolean", "Byte", "Character", "Double", "Float", "Integer", "Long", “Short" };for(int x=0;x<primitiveList.length;x++){//primitive type with '?' at endString prim = String.format("%s[?]", primitiveList[x]); if(result.contains(primitiveList[x])){//primitive type to uppercaseString upper = String.format("%SQ", primitiveList[x]);//exact match of primitive typeString result = result . replaceAll(prim, upper). replaceAll(type, objectTypeList[x]) . replaceAll(upper, primitiveList[x]);}//end if}//end forreturn result; }//end transpileCode6.3轉換然后導出到文件
在“ transpileCode()”方法將特征語法轉換為ZeptoN源代碼之后,然后將源代碼寫入外部文件。 整體“ transpile()”方法的源代碼為:
private static void transpile(String fileNameOrig) { String srcCode = "";try {srcCode = new String(Files.readAllBytes(Paths.get(fileNameOrig))); } catch (Exception ex) {System.out.printf("Failure reading source file: %s!%n", fileNameOrig);return; }//end try//transpile to ZeptoN source from extended feature syntax srcCode = transpileCode(srcCode);String path = fileNameOrig.replace(".orig", ".zep");try {Files.write(Paths.get(path), srcCode.getBytes(Charset.defaultCharset()));} catch (Exception ex) {System.out.printf("Source code write failure!%n"); return;}//end try}//end transpile“ transpile()”方法使用外部文件,“。zep”文件中的新功能語法變為“ .orig”文件。 將源代碼文件讀入字符串,然后轉換為ZeptoN源代碼。 然后將ZeptoN源代碼文件寫入“ .zep”文件。 這將保留傳遞的原始文件參數以及任何命令行參數參數。 其余編譯器使用現有的ZeptoN轉編譯器實現。
7.使用ZeptoN的轉編譯器實現
ZeptoN轉編譯器用作轉編譯器的舊版或預先存在的代碼,以集成新功能語法。 方法是:
因此,具有ZeptoN中功能語法的新轉編譯器將使用外部文件,因此不會在內部進行編譯。 這樣做的好處是,在使用新語法對ZeptoN源代碼進行預處理之后,可以將中間ZeptoN源代碼存儲為整個編譯過程的一部分。
現有的ZeptoN反編譯器(使用內存中的Java編譯器將反編譯的ZeptoN編譯為Java源代碼)用作包或庫。 因此,現有的ZeptoN編譯器不會被修改或細分,而是在編譯的最后階段使用。
7.1壓縮現有的ZeptoN Transcompiler
現有的ZeptoN轉編譯器“ Zep.java”是在Github存儲庫中發布的開源Java。 轉編譯器在內部將文件“ source.zep”中的ZeptoN源代碼轉換為Java源代碼,然后使用Java Compiler API內存將其編譯為字節碼.class文件。
Transcompiler Zep.java類的兩個核心方法當然是“ main(String [] args)”作為調用的主要方法,以及“ compile(String [] args)”方法進行實際的反編譯,然后編譯為Java字節碼.class文件。 問題是將原始類型轉換為對象包裝器類型后要調用哪種方法。 這兩個方法是“ main()”方法或“ compile()”方法,它們都是靜態的無狀態方法。
7.1.1 main()方法
ZeptoN轉編譯器“ Zep.java”具有可以使用的“ main()”方法,因為所有參數均已保留,并且使用了外部文件。 “ main()”方法的源代碼是:
public static void main(final String[] args) {try {if (args.length == 0) {System.out.printf("%s %s%n%s%n", RELEASE, VERSION, LICENSE); }//end ifZep.compile(args);} catch(Exception ex) {error("ZeptoN Compiler Exception: '%s' is '%s'.%n",ex.getClass().getName(), ex.getMessage()); ex.printStackTrace();System.exit(EXIT_CODE_FAILURE); }//end trySystem.exit(EXIT_CODE_SUCCESS); }//end main通過“ main”調用ZeptoN Transcompiler會遇到棘手的問題,因為成功或失敗都會調用“ System.exit()”。 因此,不可能使用新的語法功能編譯多個文件,因為編譯的第一個文件將在成功或失敗時終止。
7.1.2 compile()方法
ZeptoN轉編譯器方法“ compile()”由“ main()”方法調用。 該方法創建ZeptoN編譯器的實例,處理命令行參數,并配置命令行參數。 如果沒有傳遞參數,或沒有文件提供給轉編譯器,則會引發錯誤。
ZeptoN轉編譯器的“ compile()”方法的源代碼為:
public static void compile(final String[] args) {if (args.length == 0) { error(ERROR_NO_INPUT);}//end iffinal Zep comp = new Zep();comp.processCommandLineArgs(args);if (files.isEmpty()) { error(ERROR_NO_FILES);}//end ifcomp.configureParams();for (String sourceFile : files) {comp.compileZeptoN( Zep.transpile(sourceFile), sourceFile );}//end for }//end compile實際的ZeptoN轉編譯器使用“ transpile()”方法返回Java源文件對象,該對象將傳遞給編譯器實例方法“ compileZeptoN()”以生成Java字節碼.class文件。 “ transpile()”方法將外部ZeptoN源文件讀取為String對象,并轉換為Java源代碼,然后對其進行編譯。
7.1.3調用compile()方法
“ compile()”方法用于將已轉換的功能語法編譯為字節碼.class文件。 由于使用了外部文件,因此可能有兩個錯誤:
重命名文件,然后將新語法功能轉換為ZeptoN源代碼后,將調用ZeptoN轉編譯器“ compile()”,然后ZeptoN轉編譯器將完成轉碼為Java字節碼.class文件的工作。
之后,在刪除中間的“ .zep”文件后,將重命名文件“ .orig”中具有新功能語法的原始源代碼文件。 “ compile()”方法中此步驟的源代碼為:
private static void compile(String[] args) { //...Zep.compile(args);for(String fileName : fileList) { Path path = Paths.get(fileName); try {Files.delete(path); } catch (Exception ex) {System.out.printf("Failure deleting file path:%s!%n", path);}//end tryString fileNameOrig = fileName.replace(".zep", ".orig");Path oldFile = Paths.get(fileNameOrig); Path newFile = Paths.get(fileName);try {Files.move(oldFile, newFile, StandardCopyOption.REPLACE_EXISTING); } catch (Exception ex) {System.out.printf("Error: Unable to rename file %s!%n", oldFile); }//end try}//end for}//end transpile成功刪除中間文件并將“ .orig”源代碼文件重命名為“ .zep”后,反編譯過程即告完成。
7.1.4擴展功能語法轉譯器摘要
將新語法功能轉換為Java字節碼.class文件的整個過程使用外部文件,因此大部分過程是重命名,刪除,讀取和寫入源代碼文件。 但是所有這些數據移動都允許使用帶有編譯器參數和文件名的“ compile()”來調用現有的ZeptoN轉編譯器。 整個過程是:
7.2測試新的語法功能
新語法功能的實現已完成,但是現在可以測試ZeptoN編程語言中添加的新功能。
測試新的語法功能將使用四個ZeptoN源文件。 使用原始的ZeptoN編譯器,該測試很簡單: 以及改良的ZeptoN編譯器:ZepPTO。 測試中使用的ZeptoN源代碼文件是:
Zep原始的ZeptoN源代碼編譯器將編譯所有ZeptoN源文件,但包含新功能語法的'polyMathSyntax.zep'除外。 ZepPTO擴展的特色語法編譯器將編譯所有文件。
由于除“ polyMathSyntax.zep”以外的所有文件都將編譯,否則該文件將因Zep反編譯器而失敗,但因ZepPTO反編譯器而成功,因此使用此文件的輸出進行比較,以避免不必要的重復和解釋。
7.2.1使用ZeptoN編譯新語法
當使用ZeptoN轉編譯器進行編譯時,結果為:
圖1:ZeptoN編譯器錯誤有11個錯誤,主要與新語法有關,不足為奇,因為現有的ZeptoN轉編譯器尚未實現新語法功能。
7.2.2使用ZepPTO的轉編譯器
使用新的ZepPTO(提升為對象)轉編譯器進行編譯時,結果為:
/Users/williamgilreath$java javacodegeeks.zepton.ZepPTO -echo polyMathSyntax.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathSyntax.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathSyntax.zep' is: Success.現在運行生成的Java字節碼.class文件,結果是:
/Users/williamgilreath$java -cp . javacodegeeks.polyMathSyntax Total time: 301515 nanosec將ZeptoN源代碼轉換為字節碼.class文件可使用Java運行時運行。
7.2.3使用Zep編譯其他文件
其他具有常規ZeptoN語法的ZeptoN源文件是使用未擴展的ZeptoN轉編譯器“ Zep”和參數“ -echo”來編譯的,以回顯所使用的Javac參數以及編譯器的整體成功或失敗。
/Users/williamgilreath$java io.github.wgilreath.ZeptoN.Zep -echo polyMathObject.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathObject.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathObject.zep' is: Success.常規的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathObject.zep”。
/Users/williamgilreath$java io.github.wgilreath.ZeptoN.Zep -echo polyMathPrimitive1.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathPrimitive1.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathPrimitive1.zep' is: Success.常規的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathPrimitive1.zep”。
/Users/williamgilreath$java io.github.wgilreath.ZeptoN.Zep -echo polyMathPrimitive2.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathPrimitive2.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathPrimitive2.zep' is: Success.常規的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathPrimitive2.zep”。
7.2.4使用ZepPTO編譯其他文件
其他具有常規ZeptoN語法的ZeptoN源文件將通過擴展的ZeptoN轉編譯器“ ZepPTO”與參數“ -echo”一起進行編譯,以回顯所使用的Javac參數以及編譯器的整體成敗。
/Users/williamgilreath$java javacodegeeks.zepton.ZepPTO -echo polyMathObject.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathObject.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathObject.zep' is: Success.擴展的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathObject.zep”。
/Users/williamgilreath$java javacodegeeks.zepton.ZepPTO -echo polyMathPrimitive1.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathPrimitive1.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathPrimitive1.zep' is: Success.擴展的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathPrimitive1.zep”。
/Users/williamgilreath$java javacodegeeks.zepton.ZepPTO -echo polyMathPrimitive2.zep ZeptoN Compiler Options: [-d, /Users/williamgilreath, -g] Files: [polyMathPrimitive2.zep] Encoding: UTF-8 ZeptoN Compiler result for file: 'polyMathPrimitive2.zep' is: Success.擴展的ZeptoN編譯器已成功編譯ZeptoN源文件“ polyMathPrimitive2.zep”。
7.2.5測試總結
通過兩個轉編譯器對常規ZeptoN源文件和擴展語法功能的測試表明,擴展轉編譯器ZepPTO可編譯為Java字節碼.class文件。 新功能語法可將基本類型提升為對象類型包裝程序,并使用新功能語法排除基本類型以保持基本類型。
8.結論
ZeptoN編程語言是Java,僅關注程序實體,這是Java編程語言所缺乏的功能。 這將創建一種與Java語法相似且兼容的編程語言。 這樣的編程語言可以輕松地反編譯為Java源代碼,然后使用Java Compiler API編譯為字節碼.class文件。
ZeptoN編程語言通過添加具有新語法的新功能進行了擴展。 此功能是將原始類型(不包括null和void)轉換為對象包裝器類型。 這是編程語言的一個常見主題,通常在極端情況下被稱為“蠕動性胎炎”或“特征蠕變”。 但是,對于編程語言語法中的新功能,必須對其進行設計和實現。
新功能語法是通過使用將新功能語法的ZeptoN源代碼轉換為普通ZeptoN源代碼的轉編譯器來實現的。 使用現有的ZeptoN反編譯器將源代碼反編譯為Java字節碼。 這具有將現有的Transcompiler用于ZeptoN的優點,但是可以通過新功能自定義和擴展語言。 這樣可以避免對ZeptoN中添加的新語法功能進行全新的實現
因此,重點是實現針對新語法功能的編譯器,然后實施,利用現有的編譯器和編譯器,因為ZeptoN編譯器先編譯為Java源代碼,然后再編譯為Java字節碼.class文件。 可以使用相同的方法來通過新功能擴展Java,使用WEJAC編譯器[Gilr 2019b]將轉編譯后的Java源代碼編譯為純Java源代碼,然后編譯為字節碼.class文件。
9.參考
[Alpe 2000] Alpert,ShermanR。“原始類型被認為有害”。
英國文化協會,《 更多的Java寶石》 ,劍橋大學出版社,紐約,紐約,2000年,第435-454頁。[英國2019年]。
“認知超載”,2015年5月20日, https://www.teachingenglish.org.uk/article/cognitive-overload 。
于2019年11月9日訪問。[Cope 2009] Tom Copeland。
用JavaCC生成解析器 ,《百年紀念書》,弗吉尼亞州亞歷山大市,2009年,第29頁。[Ecke 2003] Eckel,Bruce。
《用Java思考》 ,Prentice-Hall,上薩德爾河,新澤西州,2003年,第3頁。
90 [Gilr 2019a] Gilreath,William F.GitHub存儲庫“ WEJAC:Will's Elided Java API編譯器,'' https ://wgilreath.github.io/WEJAC/.2019年12月31日訪問。[Gilr2019b] Gilreath,William F.GitHub存儲庫“ ZepC – ZeptoN Echo Transcompiler”, https: //wgilreath.github.io/ZeptoN/于2019年12月31日訪問。[Moor 2014] Moore,John。
“ Java中保留原語的案例”,JavaWorld, https: //www.javaworld.com/article/2150208/a-case-for-keeping-primitives-in-java.html。
2014年5月。于2019年12月27日訪問。[Orac 2019] Oracle America,Inc.,Java語言規范,第13版, https: //docs.oracle.com/javase/specs/jls/se13/jls13.pdf。
訪問于2019年12月27日。[Wiki 2019a] Wikibooks,Java編程。
WikiBooks Edition, https ://en.wikibooks.org/wiki/Java_Programming/Keywords/void。
于2019年12月30日訪問。[Wiki 2019b] Wikibooks。
BASIC編程,2019年10月13日.https ://en.wikibooks.org/wiki/BASIC_Programming/Beginning_BASIC/User_Input,2019年11月9日訪問。
10.下載源代碼
下載您可以在此處下載此示例的完整源代碼: ZeptoN正在將程序放入Java中
翻譯自: https://www.javacodegeeks.com/zepton-is-putting-program-into-java.html
總結
以上是生活随笔為你收集整理的ZeptoN正在将程序放入Java的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 一纳米等于多少米 一纳米是多少米
- 下一篇: 分披萨问题_比萨问题–建造者与装饰者