本發(fā)明涉及一種代碼運(yùn)行系統(tǒng)及其方法,尤其涉及一種動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng)及其方法。
背景技術(shù):
在一個(gè)應(yīng)用里面,接收外部代碼片段,進(jìn)行動(dòng)態(tài)編譯和運(yùn)行,返回運(yùn)行結(jié)果。此技術(shù)主要用于編程技術(shù)的在線教學(xué)、作業(yè)、測(cè)評(píng)、考試、模擬回放等技術(shù)領(lǐng)域。
一般而言,所有在線編程的產(chǎn)品都需要一個(gè)運(yùn)行引擎的支持,同類(lèi)產(chǎn)品的特點(diǎn)是能編譯運(yùn)行外部代碼,一次性返回所有結(jié)果。但是,同類(lèi)產(chǎn)品無(wú)法解決以下問(wèn)題:
1)外部代碼存在時(shí)間延遲,需要多次返回;2)外部代碼存在輸入輸出,如先提示,等待用戶(hù)輸入,再輸出;3)外部代碼里有多線程,持續(xù)不斷的輸出;4)外部代碼有死循環(huán),在死循環(huán)里不斷輸出,需要能持續(xù)輸出,超時(shí)自動(dòng)停止。
以上這些問(wèn)題,在編程語(yǔ)言的學(xué)習(xí)中都是很重要的內(nèi)容,如果解決不了,則教學(xué)就不能達(dá)到很好的效果。
技術(shù)實(shí)現(xiàn)要素:
本發(fā)明為了克服現(xiàn)有技術(shù)的不足,提供一種動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng)及其方法,支持所有的編程語(yǔ)言,支持對(duì)外部代碼的各種管理流程,為外部代碼里面的演示輸出、輸入輸出、多線程、死循環(huán)等內(nèi)容運(yùn)行上的技術(shù)難點(diǎn)提供解決方案。
為此,本發(fā)明采用如下技術(shù)方案:
一種動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng),包括:
主應(yīng)用,并設(shè)定主應(yīng)用為調(diào)用者,其中,主應(yīng)用指接收用戶(hù)輸入的代碼及輸入信息的應(yīng)用,調(diào)用代碼運(yùn)行引擎并返回輸出信息給用戶(hù);
運(yùn)行主線程:負(fù)責(zé)獨(dú)立編譯運(yùn)行一段代碼,由于每段代碼都在一個(gè)運(yùn)行主線程里面運(yùn)行,多用戶(hù)可以互不影響;
超時(shí)控制線程:負(fù)責(zé)監(jiān)控某段代碼的運(yùn)行是否超時(shí),如果超時(shí)則停止運(yùn)行并調(diào)用超時(shí)事件。
進(jìn)一步地,所述運(yùn)行主線程包括:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分組成,其中:Runtime的exec方法調(diào)用命令行編譯和運(yùn)行指令,自動(dòng)生成一個(gè)運(yùn)行進(jìn)程,執(zhí)行代碼的編譯運(yùn)行;輸入接口負(fù)責(zé)接收主應(yīng)用上用戶(hù)的輸入信息,發(fā)送給運(yùn)行進(jìn)程的輸入流,由運(yùn)行進(jìn)程接收處理;輸出接口負(fù)責(zé)監(jiān)聽(tīng)運(yùn)行進(jìn)程的輸出流,當(dāng)由輸出信息產(chǎn)生時(shí),讀取信息,發(fā)送給主應(yīng)用進(jìn)行顯示。
進(jìn)一步地,所述:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分都以獨(dú)立線程的方式存在,互不干擾。
本發(fā)明的另一方面,提供一種動(dòng)態(tài)編譯運(yùn)行外部代碼的方法,包括如下步驟:
S1:設(shè)定某一主應(yīng)用為調(diào)用者,其中,主應(yīng)用指接收用戶(hù)輸入的代碼及輸入信息的應(yīng)用,調(diào)用代碼運(yùn)行引擎并返回輸出信息給用戶(hù);
S2:運(yùn)行主應(yīng)用 ,啟動(dòng)運(yùn)行主線程,其中,運(yùn)行主線程為負(fù)責(zé)獨(dú)立編譯運(yùn)行一段代碼;
S3:?jiǎn)?dòng)超時(shí)控制線程,超時(shí)控制線程在啟動(dòng)運(yùn)行主線程開(kāi)始后的設(shè)定時(shí)間內(nèi)對(duì)運(yùn)行主線程進(jìn)行檢查,判斷運(yùn)行主線程是否存活:
如果還存活則認(rèn)定為超時(shí),結(jié)束運(yùn)行主線程并觸發(fā)超時(shí)處理事件;
如果運(yùn)行的代碼在三分鐘內(nèi)正常運(yùn)行結(jié)束,則運(yùn)行主線程乃至其中的運(yùn)行進(jìn)程+輸入接口+輸出接口都會(huì)被結(jié)束并自動(dòng)銷(xiāo)毀,之后超時(shí)線程會(huì)認(rèn)定運(yùn)行主線程已正常結(jié)束;
如果運(yùn)行的代碼存在死循環(huán),則超時(shí)控制線程會(huì)認(rèn)定運(yùn)行主線程為超時(shí);
如果運(yùn)行的代碼有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)被阻塞等待用戶(hù)輸入,之后如果用戶(hù)一直沒(méi)有輸入,則超時(shí)控制程序也會(huì)認(rèn)定運(yùn)行主線程為超時(shí);
如果阻塞等待輸入后,用戶(hù)有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)繼續(xù)往下執(zhí)行直至結(jié)束,之后超時(shí)控制線程會(huì)認(rèn)定為正常結(jié)束。
進(jìn)一步地,所述運(yùn)行主線程包括:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分組成,其中:Runtime的exec方法調(diào)用命令行編譯和運(yùn)行指令,自動(dòng)生成一個(gè)運(yùn)行進(jìn)程,執(zhí)行代碼的編譯運(yùn)行;輸入接口負(fù)責(zé)接收主應(yīng)用上用戶(hù)的輸入信息,發(fā)送給運(yùn)行進(jìn)程的輸入流,由運(yùn)行進(jìn)程接收處理;輸出接口負(fù)責(zé)監(jiān)聽(tīng)運(yùn)行進(jìn)程的輸出流,當(dāng)由輸出信息產(chǎn)生時(shí),讀取信息,發(fā)送給主應(yīng)用進(jìn)行顯示。
進(jìn)一步地,所述:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分都以獨(dú)立線程的方式存在,互不干擾。
本發(fā)明具有如下有益效果:
1.本動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng),系統(tǒng)架構(gòu)上是開(kāi)放的,能非常方便的擴(kuò)展更多的編程語(yǔ)言;
2. 系統(tǒng)對(duì)每份運(yùn)行的代碼都是線程隔離的,不同用戶(hù)之間互不影響,即使有代碼是死循環(huán),也不會(huì)影響其它代碼運(yùn)行;
3.本產(chǎn)品在底層封裝了運(yùn)行的具體細(xì)節(jié),以事件驅(qū)動(dòng)的方式提供接口給應(yīng)用層,性能非常高,適合用來(lái)實(shí)現(xiàn)大規(guī)模在線教學(xué)應(yīng)用。
附圖說(shuō)明
圖1為本發(fā)明中命令行調(diào)用的示意圖;
圖2、圖3為本發(fā)明的動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng)的結(jié)構(gòu)框圖。
具體實(shí)施方式
為了使本技術(shù)領(lǐng)域的人員更好的理解發(fā)明方案,下面將結(jié)合具體實(shí)施例及附圖,對(duì)發(fā)明的技術(shù)方案進(jìn)行清楚、完整的描述。
實(shí)施例1:
如圖2、圖3所示,一種動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng),包括:
主應(yīng)用,設(shè)定主應(yīng)用為調(diào)用者,其中,主應(yīng)用指接收用戶(hù)輸入的代碼及輸入信息的應(yīng)用,調(diào)用代碼運(yùn)行引擎并返回輸出信息給用戶(hù);
運(yùn)行主線程:負(fù)責(zé)獨(dú)立編譯運(yùn)行一段代碼,由于每段代碼都在一個(gè)運(yùn)行主線程里面運(yùn)行,多用戶(hù)可以互不影響;
運(yùn)行主線程包括:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分組成,其中:Runtime的exec方法調(diào)用命令行編譯和運(yùn)行指令,自動(dòng)生成一個(gè)運(yùn)行進(jìn)程,執(zhí)行代碼的編譯運(yùn)行;輸入接口負(fù)責(zé)接收主應(yīng)用上用戶(hù)的輸入信息,發(fā)送給運(yùn)行進(jìn)程的輸入流,由運(yùn)行進(jìn)程接收處理;輸出接口負(fù)責(zé)監(jiān)聽(tīng)運(yùn)行進(jìn)程的輸出流,當(dāng)由輸出信息產(chǎn)生時(shí),讀取信息,發(fā)送給主應(yīng)用進(jìn)行顯示;由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分都以獨(dú)立線程的方式存在,互不干擾。
超時(shí)控制線程:負(fù)責(zé)監(jiān)控某段代碼的運(yùn)行是否超時(shí),如果超時(shí)則停止運(yùn)行并調(diào)用超時(shí)事件。
下述為對(duì)本發(fā)明動(dòng)態(tài)編譯運(yùn)行外部代碼的系統(tǒng)的詳細(xì)說(shuō)明:
1、命令行調(diào)用:任何語(yǔ)言都存在編譯和運(yùn)行的命令行指令,例如:C/C++用gcc命令編譯,用文件名運(yùn)行;而java使用javac命令進(jìn)行編譯,用java命令進(jìn)行運(yùn)行。在JAVA應(yīng)用里面通過(guò)調(diào)用Runtime接口,即可調(diào)用外部命令行指令,通過(guò)封裝以上每種語(yǔ)言的命令行指令,即可實(shí)現(xiàn)基本的編譯和運(yùn)行功能,如圖1所示;
2、輸入輸出接口:當(dāng)調(diào)用Runtime.exec執(zhí)行外部指令時(shí),jvm會(huì)啟動(dòng)一個(gè)運(yùn)行進(jìn)程進(jìn)行調(diào)用,此時(shí)此進(jìn)程擁有自己的輸入輸出流,而主應(yīng)用的進(jìn)程需要接管運(yùn)行進(jìn)程的輸入輸出流,如圖2所示;
其中:
輸入接口和輸出接口都是以線程的方式存在,與主進(jìn)程(運(yùn)行進(jìn)程)獨(dú)立,互不干擾;
當(dāng)運(yùn)行進(jìn)程有產(chǎn)生輸出時(shí)(如代碼里的printf語(yǔ)句),輸出接口會(huì)讀取到運(yùn)行進(jìn)程的輸出流產(chǎn)生的輸出信息,發(fā)送給主應(yīng)用進(jìn)行顯示;
當(dāng)主應(yīng)用上用戶(hù)輸入時(shí),通過(guò)輸入接口發(fā)送給運(yùn)行進(jìn)程,運(yùn)行進(jìn)程的輸入流接收到輸入信息,進(jìn)行處理。
通過(guò)以上獨(dú)立的輸入輸出接口的設(shè)計(jì),引擎實(shí)現(xiàn)了幾個(gè)場(chǎng)景:
(1)延遲輸出:不管什么時(shí)候產(chǎn)生輸出,輸出接口都能捕獲,發(fā)送給主應(yīng)用顯示。
(2)多線程輸出:多線程共享運(yùn)行進(jìn)程的輸出流,按照次序都會(huì)被輸出接口捕獲,依次發(fā)送給主應(yīng)用顯示。
(3)輸入:當(dāng)代碼需要等待輸入時(shí),運(yùn)行進(jìn)程會(huì)被自動(dòng)阻塞,等待輸入接口的信息。當(dāng)接收到輸入信息時(shí)才會(huì)解除阻塞進(jìn)行處理。
(4)輸出輸入配合:如果代碼的邏輯是先提示用戶(hù)輸入,然后對(duì)用戶(hù)輸入進(jìn)行處理,則按照時(shí)間順序,主應(yīng)用會(huì)先接收輸出并顯示第一次輸出的提示信息,然后發(fā)送用戶(hù)的輸入給輸入接口,再接收到處理后的輸出信息并顯示。例如:
第一次輸出:“請(qǐng)輸入您的姓名:”
等待用戶(hù)輸入:“張三”
第二次輸出:“張三先生,歡迎您”。
3、超時(shí)處理
通常代碼執(zhí)行結(jié)束,運(yùn)行進(jìn)程也就自動(dòng)被銷(xiāo)毀,但有時(shí)代碼可能存在死循環(huán)或者輸入代碼但用戶(hù)不輸入的情況,此時(shí)運(yùn)行進(jìn)程會(huì)一直結(jié)束不了,此時(shí)就需要設(shè)計(jì)一種超時(shí)處理機(jī)制,以釋放長(zhǎng)時(shí)間不結(jié)束的運(yùn)行進(jìn)程。
把以上調(diào)用邏輯給封裝進(jìn)一個(gè)獨(dú)立線程執(zhí)行,在此獨(dú)立線程之外通過(guò)一個(gè)超時(shí)控制線程來(lái)控制是否超時(shí),如果超時(shí)就自動(dòng)停止運(yùn)行并銷(xiāo)毀有關(guān)資源,如圖3所示;
其中:
(1)當(dāng)主應(yīng)用啟動(dòng)運(yùn)行主線程之后,即刻啟動(dòng)一個(gè)超時(shí)控制線程,超時(shí)控制線程會(huì)在啟動(dòng)固定時(shí)間(預(yù)先配置的時(shí)間,如3分鐘)之后對(duì)運(yùn)行主線程進(jìn)行檢查,判斷運(yùn)行主線程是否存活,如果還存活則認(rèn)定為超時(shí),結(jié)束運(yùn)行主線程并觸發(fā)超時(shí)處理事件。
(2)如果運(yùn)行的代碼在三分鐘內(nèi)正常運(yùn)行結(jié)束,則運(yùn)行主線程乃至其中的運(yùn)行進(jìn)程+輸入接口+輸出接口都會(huì)被結(jié)束并自動(dòng)銷(xiāo)毀,之后超時(shí)線程會(huì)認(rèn)定運(yùn)行主線程已正常結(jié)束。
(3)如果運(yùn)行的代碼存在死循環(huán),則超時(shí)控制線程會(huì)認(rèn)定運(yùn)行主線程為超時(shí)。
(4)如果運(yùn)行的代碼有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)被阻塞等待用戶(hù)輸入,之后如果用戶(hù)一直沒(méi)有輸入,則超時(shí)控制程序也會(huì)認(rèn)定運(yùn)行主線程為超時(shí)。
(5)接上,如果阻塞等待輸入后,用戶(hù)有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)繼續(xù)往下執(zhí)行直至結(jié)束,之后超時(shí)控制線程會(huì)認(rèn)定為正常結(jié)束。
實(shí)施例2:
一種動(dòng)態(tài)編譯運(yùn)行外部代碼的方法,如圖3所示,包括如下步驟:
S1:設(shè)定某一主應(yīng)用為調(diào)用者,其中,主應(yīng)用指接收用戶(hù)輸入的代碼及輸入信息的應(yīng)用,調(diào)用代碼運(yùn)行引擎并返回輸出信息給用戶(hù);
S2:運(yùn)行主應(yīng)用 ,啟動(dòng)運(yùn)行主線程,其中,運(yùn)行主線程為負(fù)責(zé)獨(dú)立編譯運(yùn)行一段代碼;
所述運(yùn)行主線程包括:由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分組成,其中:Runtime的exec方法調(diào)用命令行編譯和運(yùn)行指令,自動(dòng)生成一個(gè)運(yùn)行進(jìn)程,執(zhí)行代碼的編譯運(yùn)行;輸入接口負(fù)責(zé)接收主應(yīng)用上用戶(hù)的輸入信息,發(fā)送給運(yùn)行進(jìn)程的輸入流,由運(yùn)行進(jìn)程接收處理;輸出接口負(fù)責(zé)監(jiān)聽(tīng)運(yùn)行進(jìn)程的輸出流,當(dāng)由輸出信息產(chǎn)生時(shí),讀取信息,發(fā)送給主應(yīng)用進(jìn)行顯示;由Runtime發(fā)起的運(yùn)行進(jìn)程、輸入接口、輸出接口三部分都以獨(dú)立線程的方式存在,互不干擾;
S3:?jiǎn)?dòng)超時(shí)控制線程,超時(shí)控制線程在啟動(dòng)運(yùn)行主線程開(kāi)始后的設(shè)定時(shí)間內(nèi)對(duì)運(yùn)行主線程進(jìn)行檢查,判斷運(yùn)行主線程是否存活:
如果還存活則認(rèn)定為超時(shí),結(jié)束運(yùn)行主線程并觸發(fā)超時(shí)處理事件;
如果運(yùn)行的代碼在三分鐘內(nèi)正常運(yùn)行結(jié)束,則運(yùn)行主線程乃至其中的運(yùn)行進(jìn)程+輸入接口+輸出接口都會(huì)被結(jié)束并自動(dòng)銷(xiāo)毀,之后超時(shí)線程會(huì)認(rèn)定運(yùn)行主線程已正常結(jié)束;
如果運(yùn)行的代碼存在死循環(huán),則超時(shí)控制線程會(huì)認(rèn)定運(yùn)行主線程為超時(shí);
如果運(yùn)行的代碼有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)被阻塞等待用戶(hù)輸入,之后如果用戶(hù)一直沒(méi)有輸入,則超時(shí)控制程序也會(huì)認(rèn)定運(yùn)行主線程為超時(shí);
如果阻塞等待輸入后,用戶(hù)有輸入,此時(shí)運(yùn)行進(jìn)程會(huì)繼續(xù)往下執(zhí)行直至結(jié)束,之后超時(shí)控制線程會(huì)認(rèn)定為正常結(jié)束。
將本發(fā)明應(yīng)用在線教學(xué)領(lǐng)域,可以獲得如下有益效果:
在編程語(yǔ)言的教學(xué)過(guò)程中,能夠?qū)崿F(xiàn)代碼編寫(xiě)的演示、練習(xí)等過(guò)程放到云平臺(tái)中去,以便老師和學(xué)生能夠隨時(shí)動(dòng)手實(shí)踐,并看到運(yùn)行的結(jié)果,促進(jìn)教學(xué)效率;
在編程測(cè)評(píng)過(guò)程中,能夠?qū)崿F(xiàn)根據(jù)不同的輸入數(shù)據(jù),輸出對(duì)應(yīng)的結(jié)果,以便系統(tǒng)能進(jìn)行自動(dòng)評(píng)分;
在引導(dǎo)式學(xué)習(xí)過(guò)程中,能夠?qū)崿F(xiàn)提示用戶(hù)輸入,然后根據(jù)用戶(hù)的輸入輸出對(duì)應(yīng)結(jié)果,讓用戶(hù)對(duì)編程有更加直觀的認(rèn)知;
在在線編程教材中,能夠支持輸入輸出、多線程、延遲輸出、死循環(huán)等重要的內(nèi)容,讓學(xué)生對(duì)這些內(nèi)容能有更加直觀的理解。