日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

从零写一个编译器(完结):总结和系列索引

發布時間:2023/12/20 编程问答 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 从零写一个编译器(完结):总结和系列索引 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

前言

這個系列算作我自己的學習筆記,到現在已經有十三篇了,加上這篇一共十四篇。一步一步的從詞法分析到語法分析、語義分析,再到代碼生成,準備在這一篇做一個總結收尾和一個這個系列以前文章的索引。

(另外,由于我現在的這個主題不能對markdown的一級標題作目錄,所以這個系列文章的目錄都是有問題的)

索引

從零寫一個編譯器(一):輸入系統和詞法分析

從零寫一個編譯器(二):語法分析之前置知識

從零寫一個編譯器(三):語法分析之幾個基礎數據結構

從零寫一個編譯器(四):語法分析之構造有限狀態自動機

從零寫一個編譯器(五):語法分析之自動機的缺陷和改進

從零寫一個編譯器(六):語法分析之表驅動語法分析

從零寫一個編譯器(七):語義分析之符號表的數據結構

從零寫一個編譯器(八):語義分析之構造符號表

從零寫一個編譯器(九):語義分析之構造抽象語法樹(AST)

從零寫一個編譯器(十):編譯前傳之直接解釋執行

從零寫一個編譯器(十一):代碼生成之Java字節碼基礎

從零寫一個編譯器(十二):代碼生成之生成邏輯

從零寫一個編譯器(十三):代碼生成之遍歷AST

示例

對于C語言的一個快速排序

void quicksort(int A[10], int p, int r) {int x;int i;i = p - 1;int j;int t;int v;v = r - 1;if (p < r) {x = A[r];for (j = p; j <= v; j++) {if (A[j] <= x) {i++;t = A[i];A[i] = A[j];A[j] = t;}}v = i + 1;t = A[v];A[v] = A[r];A[r] = t;t = v - 1;quicksort(A, p, t);t = v + 1;quicksort(A, t, r);} }void main () {int a[10];int i;int t;printf("before quick sort:");for(i = 0; i < 10; i++) {t = (10 - i);a[i] = t;printf("value of a[%d] is %d", i, a[i]);}quicksort(a, 0, 9);printf("after quick sort:");for (i = 0; i < 10; i++) {printf("value of a[%d] is %d", i, a[i]);} }

解釋執行

就直接在控制臺輸出

代碼生成

會在當前目錄生成一個C2Bytecode.j字節碼文件,再經過字節碼的匯編器就可以在JVM上運行

.class public C2Bytecode .super java/lang/Object.method public static main([Ljava/lang/String;)Vsipush 10newarray intastore 0sipush 0istore 2sipush 0istore 1getstatic java/lang/System/out Ljava/io/PrintStream;ldc "before quick sort:"invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc " "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vsipush 0istore 2loop0:iload 2sipush 10 if_icmpge branch0sipush 10iload 2isubistore 1aload 0iload 2iload 1iastoreaload 0iload 2ialoadistore 3iload 2istore 4getstatic java/lang/System/out Ljava/io/PrintStream;ldc "value of a["invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;iload 4invokevirtual java/io/PrintStream/print(I)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc "] is "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;iload 3invokevirtual java/io/PrintStream/print(I)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc " "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Viload 2sipush 1iaddistore 2 goto loop0 branch0:aload 0sipush 0sipush 9invokestatic C2Bytecode/quicksort([III)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc "after quick sort:"invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc " "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vsipush 0istore 2loop2:iload 2sipush 10 if_icmpge branch4aload 0iload 2ialoadistore 3iload 2istore 4getstatic java/lang/System/out Ljava/io/PrintStream;ldc "value of a["invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;iload 4invokevirtual java/io/PrintStream/print(I)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc "] is "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Vgetstatic java/lang/System/out Ljava/io/PrintStream;iload 3invokevirtual java/io/PrintStream/print(I)Vgetstatic java/lang/System/out Ljava/io/PrintStream;ldc " "invokevirtual java/io/PrintStream/print(Ljava/lang/String;)Viload 2sipush 1iaddistore 2 goto loop2 branch4:return .end method .method public static quicksort([III)Vsipush 0istore 5sipush 0istore 6iload 1sipush 1isubistore 6sipush 0istore 7sipush 0istore 3sipush 0istore 4iload 2sipush 1isubistore 4iload 1iload 2 if_icmpge branch1aload 0iload 2ialoadistore 5iload 1istore 7loop1:iload 7iload 4 if_icmpgt ibranch1aload 0iload 7ialoadiload 5 if_icmpgt ibranch2iload 6sipush 1iaddistore 6aload 0iload 6ialoadistore 3aload 0iload 6aload 0iload 7ialoadiastoreaload 0iload 7iload 3iastore ibranch2:iload 7sipush 1iaddistore 7 goto loop1ibranch1:iload 6sipush 1iaddistore 4aload 0iload 4ialoadistore 3aload 0iload 4aload 0iload 2ialoadiastoreaload 0iload 2iload 3iastoreiload 4sipush 1isubistore 3aload 0iload 1iload 3invokestatic C2Bytecode/quicksort([III)Viload 4sipush 1iaddistore 3aload 0iload 3iload 2invokestatic C2Bytecode/quicksort([III)V branch1:return .end method.end class

總結

  • 詞法分析

一般用有限狀態自動機或者手工編寫來實現,這一步輸出的是token序列

  • 語法分析

主要分為自頂向下和自底向上的語法分析,一般有遞歸下降,LL(1),LR(1),LALR(1)幾種方法實現。這一步輸出的是語法樹

  • 語義分析

語義分析主要任務是生成符號表,并且發現不符合語義的語句,這一步輸出的還是AST

  • 代碼生成

這里一般會生成一個與平臺無關的較為貼近底層的中間語言(IR),這一步輸入AST,輸出的是IR

這個編譯過程在第一篇的時候就有提起,現在主要想總結的是解釋執行和代碼生成部分,也就是遍歷AST的過程

  • 首先抽象語法樹AST的構造就像是把所有代碼分割成一塊一塊,但是其中塊和塊之間又有邏輯關系,然后把它們組成一棵樹

  • 正是有這顆樹我們才得以對代碼進行邏輯的解釋,從葉子節點開始,再存儲處理后的信息,傳遞至父節點

  • 比如對于a = 0節點,我們先遞歸至子節點,求出a和0的值并且保存在自己的節點,而父節點a = 0就可以利用子節點的信息來對a賦值,比如如果是生成代碼的話,a = 0這個節點的操作可能就是找到這個存儲這個變量的寄存器,然后生成對這個寄存器賦值的指令

  • 在這個過程有一個非常重要的數據結構,即符號表,無論是直接解釋執行還是代碼生成都會用到。它的主要用來標識和存儲源代碼的變量、函數等。在符號表中,源程序中的每個標識符都和它的聲明或使用信息綁定在一起,比如其數據類型、作用域以及內存地址。

  • 一個玩具型編譯器的主體思路是很明確的,但是在實際實現當中需要考慮的細節也很多,所以才讓實現過于繁瑣

轉載于:https://www.cnblogs.com/secoding/p/11393720.html

總結

以上是生活随笔為你收集整理的从零写一个编译器(完结):总结和系列索引的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。