Linux-C

Linux-Cphp

1. C程序
 1.1 最簡單的C程序hello.c
 1.2 多個源碼文件
 1.3 頭文件(include)和目錄
 1.4 C預處理器
 1.5 鏈接庫
 1.6 共享庫
  1.6.1 列出共享庫的依賴關係
  1.6.2 ld.so怎樣找到共享庫
  1.6.3 環境變量LD_LIBRARY_PATH
2. 編譯管理工具make
 2.1 make經常使用選項
 2.2 make經常使用變量
 2.3 makefile常見的宏
 2.4 makefile常規目標
 2.5 教程手冊
 2.6 GNU autotools 安裝步驟
 2.7 configure 經常使用的選項
 2.8 Autotools的基礎知識(Gentoo開發人員手冊)
 2.9 更多相關連接
3. 調試器gdb
4. Lex和Yacc
5. 腳本語言
6. Java

 

1. C程序

最基本的生成過程: 代碼,編譯,運行. 編譯就會用到C編譯器。
來自LLVM項目的新的C編譯器clang愈來愈流行;但大部分主流的Unix系統上仍然是GNU C編譯器gcc。
html

1.1 最簡單的C程序hello.c

#include <stdio.h>

main() {
    printf("Hello, World. \n");
}

源碼文件(.c); -o編譯爲可執行文件(.out); 運行
編譯 $ cc hello.c
會產生 a.out 的可執行文件
指定文件名編譯,增長-o選項
$ cc -o hello hello.c
運行 $ ./a.out
java

1.2 多個源碼文件

多個源碼文件(.c); -c編譯爲對象文件(.o); -o鏈接爲可執行文件; 運行
main.c, aux.c ...
使用-c選項給每一個文件生成對應的對象文件
$ cc -c main.c
$ cc -c aux.c
產生對象文件: main.o, aux.o ...
對象文件是一種二進制文件。
使用鏈接器將對象文件組合爲可執行文件
$ cc -o myprog main.o aux.o

更復雜的項目, 更多個源碼文件, 須要使用make
node

1.3 頭文件(include)和目錄

保存類型和函數聲明的附加文件,好比stdio.h
Unix默認的include目錄是/usr/include, 編譯器通常就看這裏, 除非你指定其餘地方。
$ cc -c -I /usr/junk/include text.c
使用-I選項指定頭文件路徑

#include <stdio.h>
#include "myheader.h"
<*.h>頭文件在系統路徑;
"*.h"表示頭文件不在系統的include目錄中, 一般表示它與源碼在同一目錄。
python

1.4 C預處理器

並非C編譯尋找頭文件, 而是C預處理器(C preprocessor, cpp)。
C預處理器是編譯器在解析程序以前先在源碼上運行的一個東西。
C預處理器會將源碼重寫成一種編譯器能理解的形式,使源碼更易讀(並提供捷徑)。

源碼中的預處理器命令叫作指令(directive), 以#開頭, 分爲以下三種。
inculde文件: #inculde * 使預處理器將整個文件包含進來。
宏定義: #define BLAH something 預處理器會將源碼中全部BLAH替換爲something, 約定宏名爲大寫。
條件: 可用 #ifdef, #if, #endif 來對代碼進行分快。
#ifdef MACRO 指令用於檢查宏MACRO是否已定義;
#if condition 則檢查condition 是否非零。當預處理器發現if語句後的條件爲false時,就不會將#if 和 #endif 之間的代碼交給編譯器。

注:也能夠不在源碼中定義宏,而使用編譯器的-D選項,(-DBLAH=something)(#define BLAH something)
C預處理器並不懂C的任何語法,變量,函數或其餘元素,它只看宏和指令。
Unix上的C預處理器是cpp,也能夠用 gcc -E 來運行,不過通常不多須要單獨運行預處理器。
linux

1.5 鏈接庫

所謂C庫,就是一些已編譯好的,通用的,可以讓你添加到本身程序的函數。例如不少可執行程序會用到的數學庫...
庫主要實在鏈接的時候(鏈接器從對象文件產生可執行程序時)發揮做用。
默認的庫文件路徑(/usr/lib)

使用編譯器的 -l 選項鍊接庫文件。
例如這裏用到通常的gobject庫文件是libgobject.a, 而庫的名字是gobject. 因此完整的鏈接和編譯以下:
$ cc -o textp textp.o -lgobject

使用 -L 選項指定庫文件路徑
例如庫文件不在常規位置,而在/usr/junk/lib/libcrud.a
$ cc -o testp testp.o -lgobject -L/usr/junk/lib -lcrud

在庫中搜索特定的函數,使用nm命令,nm libjobject.a, (可能要用locate命令查找libjobject.a, 不少發行版會將庫放在/usr/lib特定的子目錄)
git

1.6 共享庫

名稱以.a結尾的庫是靜態庫。
鏈接靜態庫時,鏈接器會將庫文件中的機器碼複製到程序中。最終的可執行程序不須要該庫也能運行。
使用靜態庫的優勢是簡單方便,不依賴環境。缺點也很明顯:github

  •   過多使用靜態庫,會使文件愈來愈大,佔用空間。
  •   若庫裏的函數更新了,原有程序不會改變,須要從新編譯才能使用到最新的庫函數。

共享庫便可解決這些問題。引用共享庫的程序只會在須要時纔將該庫加載到內存中。並且多個進程能夠共享內存中同一個共享庫。
使用共享庫的的缺點是管理困難,鏈接複雜。但只需搞定以下問題:web

  •   如何列出程序須要的共享庫;
  •   程序如何查找共享庫;
  •   如何讓程序鏈接共享庫;
  •   常見的共享庫陷阱。

1.6.1 列出共享庫的依賴關係

共享庫和靜態庫一般放在同一個地方,Linux的兩大標準庫目錄/lib, /usr/lib. 其中/lib是不該該包含靜態庫的。
共享庫的名字後綴一般含有.so(意爲共享對象)
$ ldd /bin/bash
linux-vdso.so.1 (0x00007fff77fe7000)
libreadline.so.8 => /usr/lib/libreadline.so.8 (0x00007f60035ec000)
libdl.so.2 => /usr/lib/libdl.so.2 (0x00007f60035e7000)
libc.so.6 => /usr/lib/libc.so.6 (0x00007f6003424000)
libncursesw.so.6 => /usr/lib/libncursesw.so.6 (0x00007f60033b5000)
/lib64/ld-linux-x86-64.so.2 => /usr/lib64/ld-linux-x86-64.so.2 (0x00007f6003750000)
考慮到最佳性能和靈活性,可執行程序自己一般不知道它所用的共享庫在哪裏,只知道共享庫名字,或只知道一點點尋找共享庫的提示,如上左邊是共享庫名字。
ld.so(運行時動態鏈接器/加載器)能夠爲程序在運行時找到並加載共享庫。如上ldd輸出的右邊是ld.so找到的庫的位置。
最後一行顯示了ld.so的實際位置。
shell

1.6.2 ld.so怎樣找到共享庫

一般的順序是以下的步驟(1),(2); 特殊狀況纔會使用(0)這個步驟。

  • (0) 參考環境變量LD_LIBRARY_PATH.(沒有源碼,又不能使用patchelf指定,就能夠用這個了)
  • (1) 一般首先查找(可執行程序預先配置好的運行時搜索路徑(若是有配置) runtime library search pach, 簡稱rpath);
  • (2) 接着,會參考系統緩存/etc/ls.so.cache, 看看該庫是否在常規的位置。這是從緩存配置文件/etc/ld.so.conf中的目錄列表獲取的庫文件名字的快速緩存。

注: 如其餘配置文件同樣,ld.so.conf 可能會包含 /etc/ld.so.conf.d中的配置。
標準的庫目錄/lib和/usr/lib是隱式的,即不須要包含在如上的配置文件中。
若是改動了ld.so.conf或者改動了某個共享庫的目錄,須要重建共享庫緩存
$ ldconfig -v
-v 選項會輸出被ldcongfig添加到緩存的目錄的詳細信息和他所監測到的改動。

編譯時指定程序的rpath
$ cc -o test test.o -Wl,-rpath=/opt/obscure/lib -L/opt/obscure/lib -lweird
已編譯的程序可用pathchelf加入不一樣的rpath, 不過最好仍是在編譯時就作好。

1.6.3 環境變量LD_LIBRARY_PATH

環境變量LD_LIBRARY_PATH, 用冒號分隔多個路徑。如非必要,請勿濫用。
* 永遠都不要在啓動文件中或在編譯軟件時設置LD_LIBRARY_PATH。
在沒有源碼,又不能使用patchelf指定路徑,最後的辦法。
但也請將它嵌套進shell腳本里。例如:
#!/bin/sh
LD_LIBRARY_PATH=/opt/crummy/lib
export LD_LIBRARY_PATH
exec /opt/crummy/bin/crummy.bin $@

不使用 LD_LIBRARY_PATH 避免大部分共享庫問題,但還可能遇到應用程序接口API的改變,致使裝好的軟件異常。
最好的解決辦法就是預防,在安裝庫時也使用 -Wl, -rpath, 或者使用靜態庫。

2. 編譯管理工具make

您須要一個名爲makefile的文件來告訴您make該怎麼作。一般,makefile告訴make如何編譯和連接程序。

make有本身內置的規則,當你須要.o文件時,他就會自動去找.c文件,並會對.c文件運行cc -c命令,已達到得到.o文件的目標。
編譯時經過一個 Makefile 文件進行,把這個 Makefile 文件置於 hello.c 同一目錄下.

make命令的使用
大多數的make都支持「makefile」和「Makefile」這兩種默認文件名。
特定的Makefile,你可使用make的「-f」和「--file」參數,如:make -f Make.Linux。

Makefile對格式有要求。
註釋#開頭; 宏定義; 目標:描述; 都頂頭開始,前面不須要空格或tab縮進。
任何真實的命令前面都必需要有tab鍵(不能使用空格鍵)。

2.1 make經常使用選項

  •  -f FILE, 將FILE文件做爲makefile。
  •  -n, 顯示一次構建所要用到的命令,但並不執行。
  •  -p, 打印make的內部數據庫。
  •  -d, 打印大量調試信息。
  •  --trace, 打印跟蹤信息。

2.2 make經常使用變量

$* 當前目標的基名。 f1.txt, $*就表明這裏的f1
$< 指第一個前置條件。
$@ 寫在規則裏時,表示當前目標。
$(@D) $(@F) 分別指$@目標的目錄名和文件名。
$(<D) $(<F) 分別指$<條件的目錄名和文件名
$? 比目標更新的全部前置條件。 t: p1 p2, 若p2時間戳比t新,$?就表明p2
$^ 指全部前置條件,之間空格分隔。

 

2.3 makefile常見的宏

CFLAGS C編譯器選項。make會將這個選項做爲參數,在將.c變爲.o的階段傳給編譯器。
LDFLAGS 相似CFLAGS, 不過他是在將.o變爲可執行程序的階段傳給編譯器。
LDLIBS 若是使用了LDFLAGS,但不想庫名選項與查找路徑混在一塊兒,能夠將庫名選項寫在這裏。
CC C編譯器,默認是cc。指定爲clang可用 $ make CC=clang
CPPFLAGS C預處理器選項。make運行預處理器時,將其做爲參數。
CXXFLAGS GNU使用這個宏做爲C++編譯器選項。

 

2.4 makefile常規目標

clean 一般會吧全部對象文件和可執行程序都清掉,以便從新構建或者打包軟件。 rm -f … //這個目標無處不在
distclean 它能刪除原包之外的全部東西,包括Makefile。有些可發者更喜歡用 realclean.
//GNU autotools所生成的Makefile總會有這個目標。
install 將文件和編譯好的程序放到Makefile認爲適當的地方。可能有風險,最好先用make -n install看看會放在哪裏。
test 或 check 檢驗構建出的東西是否可用。
depend 經過編譯器的-M選項來檢查源碼,以創建依賴關係。 //這是一個不尋常的目標,由於它常常會改動Makefile自身。
all 一般是Makefile的地一個目標


https://www.gnu.org/software/make/manual/make.html#Makefile-Contents
Makefile裏主要包含了五個東西:顯式規則、隱晦規則、變量定義、文件指示和註釋。

  • 顯式規則。顯式規則說明了,如何生成一個或多的的目標文件。這是由Makefile的書寫者明顯指出,要生成的文件,文件的依賴文件,生成的命令。
  • 隱晦規則。因爲咱們的make有自動推導的功能,因此隱晦的規則可讓咱們比較粗糙地簡略地書寫Makefile,這是由make所支持的。
  • 變量的定義。在Makefile中咱們要定義一系列的變量,變量通常都是字符串,這個有點你C語言中的宏,當Makefile被執行時,其中的變量都會被擴展到相應的引用位置上。
  • 文件指示。其包括了三個部分,
    • 一個是在一個Makefile中引用另外一個Makefile,就像C語言中的include同樣;
    • 另外一個是指根據某些狀況指定Makefile中的有效部分,就像C語言中的預編譯#if同樣;
    • 還有就是定義一個多行的命令。有關這一部分的內容,我會在後續的部分中講述。
  •  註釋。Makefile中只有行註釋,和UNIX的Shell腳本同樣,其註釋是用「#」字符,這個就像C/C++中的「//」同樣。若是你要在你的Makefile中使用「#」字符,能夠用反斜框進行轉義,如:「\#」。

2.5 教程手冊

入門簡易版
https://zhuanlan.zhihu.com/p/47390641
Makefile由淺入深--教程、乾貨

《Makefile文件教程》
https://gist.github.com/isaacs/62a2d1825d04437c6f08

http://www.ruanyifeng.com/blog/2015/02/make.html
Make 命令教程  阮一峯  2015年2月20日
http://www.ruanyifeng.com/blog/2015/03/build-website-with-make.html
使用 Make 構建網站

完整版《GNU Make手冊》
https://www.gnu.org/software/make/manual/make.html

https://seisman.github.io/how-to-write-makefile/introduction.html
跟我一塊兒寫Makefile
http://www.javashuo.com/article/p-kbcqvtyr-md.html
http://www.javashuo.com/article/p-sfuuzyix-mm.html

2.6 GNU autotools 安裝步驟

GNU autoconf 是一套流行的,用於自動產生Makefile的系統。解決跨平臺的問題。
使用此套系統的包都會帶有 configure, Makefile.in, config.h.in文件。其中.in是模板文件。

默認生成的Makefile中的install目標一般使用/usr/local做爲前綴;二進制程序會去到/usr/local/bin. 庫會到/usr/local/lib.
GUN autoconf及不少其餘軟件包的默認前綴都是/usr/local。他是本地安裝軟件的傳統位置。操做系統不會更新/usr/local裏的軟件。因此更新不會是你哪裏的東西丟失。

使用這類帶配置的源碼包安裝步驟大體以下:

01 下載: 官網下載...  
02-1 驗證簽名: $ gpg --verify *.sig . 驗證簽名
02-2 驗證文件: $ md5sum 驗證文件. md5sum,sha1sum,sha256sum驗證文件。
03-1 包內容: $ tar -tvf 首先用t選項查看,避免有絕對路徑等問題;
03-2 解包: $ tar -xvf[壓縮選項] 再使用xvf[壓縮選項]解包。
04 查看說明: $ cat readme 查看自述文件,install安裝說明等
05 配置: $ ./configure 分析當前系統的特性,而後在Makefile.in文件的基礎上作一些替換,建立出適合本機的構建文件:Makefile
06-1 空跑: $ make -n 顯示一次構建所要用到的命令,但並不執行。
06-2 編譯: $ make  
07 檢查: $ make check 若瞭解程序,也但是嘗試運行生成的可執行文件。
08-1 空跑: $ make -n install 空跑一次,查看安裝那些東西到哪裏。
08-2 安裝: $ make install  
09 清理: $ make clean 清除編譯鏈接過程當中的一些臨時文件
10 卸載: $ make uninstall 卸載相關應用程序

 

2.7 configure 經常使用的選項

  • --prefix=directory:  指定安裝位置。
  • --bindir=directory: 指定可執行程序位置。
  • --sbindir=directory: 指定系統級的可執行程序位置。
  • --libdir=directory: 指定庫位置。
  • --disable-shared: 不構建共享庫(要看具體什麼庫)。
  • --with-package=directory: 告訴configure須要用到=directory: 目錄的包。當某個庫不在標準位置時,使用這個選項。但並不是全部的configure腳本都能識別這個選項。

2.8 Autotools的基礎知識(Gentoo開發人員手冊)

https://devmanual.gentoo.org/general-concepts/autotools/index.html
主要的Autotools組件
Autotools是相關軟件包的集合,當它們一塊兒使用時,消除了建立便攜式軟件所涉及的許多困難。這些工具以及一些相對簡單的上游提供的輸入文件用於爲包建立構建系統。https://devmanual.gentoo.org/general-concepts/autotools/diagram.png


在一個簡單的設置:

  • 該autoconf程序configure從任一configure.in或產生一個腳本 configure.ac(見下面的註釋)。
  • 該automake程序產生一個Makefile.in來自Makefile.am。
  • configure運行 該腳本以Makefile從 Makefile.in文件生成一個或多個文件。
  • 該make程序使用Makefile編譯程序。

...

https://wiki.gentoo.org/wiki/Autotools
Autotools是一個在開源項目中經常使用的構建系統。雖然很常見,但並不是每一個開發人員都喜歡使用自動工具。一些項目試圖避免這種構建系統。

https://devmanual.gentoo.org/eclass-reference/autotools.eclass/index.html
autotools.eclass - 從新生成auto *構建腳本
此eclass用於安全處理須要從新生成其構建腳本的自動化軟件包。若是出現錯誤,全部功能都將停止。

https://wiki.gentoo.org/wiki/Comparison_of_build_systems
構建系統的比較 - 提供各類構建系統的簡要比較。
https://en.wikipedia.org/wiki/List_of_build_automation_software#Build_script_generation_tools

2.9 更多相關連接

http://www.gnu.org/software/autoconf/
http://www.gnu.org/software/automake/

https://autotools.io/index.html
Autotools Mythbuster  Diego Elio 「Flameeyes」 Pettenò   做者和出版商 <flameeyes@flameeyes.com>
Autotools Mythbuster是一個嚴肅的Autotools指南,旨在提供GNU構建鏈中工具的完整集成視圖:autoconf,automake,libtool,pkg-config等。

https://blogs.gentoo.org/lu_zero/2009/03/24/cmake-vs-autotools-a-benchmark/

==============
https://devmanual.gentoo.org/eclass-reference/autotools-utils.eclass/index.html
autotools-utils.eclass - 基於autotools的軟件包的常見ebuild函數

==============
https://wiki.gentoo.org/wiki/Project:Quality_Assurance/Autotools_failures
本指南旨在描述使自動工具沒法在ebuild中運行的常見狀況,並提供有關如何解決這些問題的建議。
介紹
與術語自動工具,咱們一般所說的由GNU工程建立平臺和操做系統無關構建系統,開發工具autoconf,automake和libtool。雖然並不是每一個包裝都同時使用全部包裝,但大多數現代包裝都是這樣作的; 舊的包一般不使用automake和libtool替代; KDE包使用更復雜的構建系統,最終依賴於上述三個軟件。

很容易識別構建系統基於autotools的軟件包:

  • 若是有配置腳本,以及configure.in或configure.ac文件,構建系統基於autoconf ;
  • 若是各個子目錄中有一個或多個Makefile.am文件,它也是automake基於;
  • 若是有一個ltmain.sh腳本,它也在使用libtool。


要構建一個使用基於autotools的構建系統的軟件包,這些工具自己並非絕對須要的:configure腳本是一個簡單的Bourne Shell腳本(一般,但這將在最近討論)並將Makefile.in文件轉換爲簡單的Makefile的make(或者,更多的時候,gmake)。儘管它們是構建軟件的可選項,但解決諸如--as-need構建失敗或自動依賴性等問題所需的補丁一般須要從新運行工具來從新建立腳本和makefile的模板。

本指南不會說明如何使用autotools修復軟件包的錯誤,由於這是一個須要解釋不少內容的普遍主題。有關使用autotools時最多見錯誤的簡單介紹,建議使用autotools文章閱讀最佳實踐。相反,它將描述從新運行autotools致使失敗的常見狀況,不管是在重建腳本仍是在構建時。
================

https://en.wikipedia.org/wiki/GNU_Build_System
https://en.wikipedia.org/wiki/Automake
https://en.wikipedia.org/wiki/Configure_(computing)
https://en.wikipedia.org/wiki/Make_(software)
https://en.wikipedia.org/wiki/Autoconf
https://en.wikipedia.org/wiki/CMake

https://en.wikipedia.org/wiki/Meson_(software)
https://en.wikipedia.org/wiki/Configure_script
https://en.wikipedia.org/wiki/Pkg-config

https://en.wikipedia.org/wiki/GNU_Debugger
https://en.wikipedia.org/wiki/GNU_Bison
https://en.wikipedia.org/wiki/Berkeley_Yacc

https://en.wikipedia.org/wiki/GNU_Compiler_Collection
https://en.wikipedia.org/wiki/List_of_compilers
此頁面旨在列出全部當前編譯器,編譯器生成器,解釋器,轉換器,工具基礎,彙編程序,可自動執行的命令行界面(shell)等。

===========
https://en.wikipedia.org/wiki/List_of_GNU_packages
GNU包列表
GNU工具鏈
主要文章:GNU工具鏈

  • GNU Binutils - 包含GNU彙編程序(as)和GNU連接程序(ld)
  • GNU bison - 用於替換yacc的解析器生成器
  • GNU構建系統(autotools) - 包含Autoconf,Automake,Autoheader和Libtool
  • GNU Compiler Collection - 針對許多編程語言優化編譯器,包括C,C ++,Fortran,Ada和Java
  • GNU調試器(gdb) - 一種高級調試器
  • GNU m4 - 宏處理器
  • GNU make - 爲GNU製做程序

https://wiki.archlinux.org/index.php/GNU#Build_system
https://www.gnu.org/

構建系統autotools
autoconf
CMake
SCons

3. 調試器gdb

gdb 全稱是 GNU Debugger,是 GNU 開源組織發佈的一個強大的 UNIX 下的程序調試工具。
gdb 主要可幫助工程師完成下面 4 個方面的功能:

啓動程序,能夠按照工程師自定義的要求爲所欲爲的運行程序。
讓被調試的程序在工程師指定的斷點處停住,斷點能夠是條件表達式。
當程序被停住時,能夠檢查此時程序中所發生的事,並追索上文。
動態地改變程序的執行環境。

https://wiki.archlinux.org/index.php/Debug_-_Getting_Traces
https://wiki.archlinux.org/index.php/Step-by-step_debugging_guide
https://wiki.gentoo.org/wiki/Project:Quality_Assurance/Backtraces#Introducing_gdb
$ gdb -q /bin/ls
Reading symbols from /bin/ls...
(No debugging symbols found in /bin/ls)
(gdb) set args /usr/share/fonts
(gdb) run
Starting program: /usr/bin/ls /usr/share/fonts
OpenImageIO  adobe-source-code-pro  cantarell  gsfonts misc  noto-cjk
TTF      adobe-source-han-sans  encodings  mathjax noto
[Inferior 1 (process 26487) exited normally]
(gdb) q

界面友好的 Eclipse IDE 和 Emacs 系統也是Linux支持的。
想挖掘內存問題和生成統計信息,試試 Valgrind http://valgrind.org

https://www.ibm.com/developerworks/cn/linux/1508_zhangdw_gdb/index.html
使用 GDB 和 KVM 調試 Linux 內核與模塊

4. Lex和Yacc

若是你要編譯的程序須要讀取配置文件或命令,那你可能要用到Lex和Yacc。這兩個工具是用於製做編程語言的。

Lex, Lexical Analyzar 詞法分析器的生成器,能將文本內容轉換成一個個標記。
GNU/Linux版本叫作flex。可使用編譯器的-ll或-lfl鏈接器標記來鏈接Lex庫。

Yacc, Yet Another Compiler Compiler 語法解析器的生成器,能根據語法來讀取標記。
GNU的解析器是 bison。爲使生成的語法分析器能與yacc兼容,須要執行bison -y。可使用編譯器的-ly鏈接器標記來鏈接Yacc的庫。

https://www.ibm.com/developerworks/cn/linux/sdk/lex/index.html
Yacc 與 Lex 快速入門

Lex
Lex 是一種生成掃描器的工具。掃描器是一種識別文本中的詞彙模式的程序。 這些詞彙模式(或者常規表達式)在一種特殊的句子結構中定義。
Lex 和 C 是強耦合的。一個 .lex 文件(Lex 文件具備 .lex 的擴展名)經過 lex 公用程序來傳遞,並生成 C 的輸出文件。這些文件被編譯爲詞法分析器的可執行版本。

Lex 編程能夠分爲三步:
以 Lex 能夠理解的格式指定模式相關的動做。
在這一文件上運行 Lex,生成掃描器的 C 代碼。
編譯和連接 C 代碼,生成可執行的掃描器。

一個 Lex 程序分爲三個段:
第一段是 C 和 Lex 的全局聲明,第二段包括模式(C 代碼),第三段是補充的 C 函數。
例如, 第三段中通常都有 main() 函數。這些段以%%來分界。

Yacc
Yacc 表明 Yet Another Compiler Compiler。 Yacc 的 GNU 版叫作 Bison。它是一種工具,將任何一種編程語言的全部語法翻譯成針對此種語言的 Yacc 語 法解析器。它用巴科斯範式(BNF, Backus Naur Form)來書寫。按照慣例,Yacc 文件有 .y 後綴。

用 Yacc 來建立一個編譯器包括四個步驟:
經過在語法文件上運行 Yacc 生成一個解析器。
說明語法:
編寫一個 .y 的語法文件(同時說明 C 在這裏要進行的動做)。
編寫一個詞法分析器來處理輸入並將標記傳遞給解析器。 這可使用 Lex 來完成。
編寫一個函數,經過調用 yyparse() 來開始解析。
編寫錯誤處理例程(如 yyerror())。
編譯 Yacc 生成的代碼以及其餘相關的源文件。
將目標文件連接到適當的可執行解析器庫。

如同 Lex 同樣, 一個 Yacc 程序也用雙百分號分爲三段。 它們是:
聲明、語法規則和 C 代碼。

5. 腳本語言

Unix中,全部#!開頭的可執行文本文件都是腳本,後面的路徑是該腳本的解釋器。
#!/usr/bin/python
#!/usr/bin/env python
#!/usr/bin/tail -2

常見的腳本語言

  • Python: 文本處理,數據庫訪問,網絡編程,多線程等,支持者衆多。還有強大的交互模式和一套有組織的對象模型。David M. Beazley, Python Essential Reference, 4th edition (Addison-Wesley, 2009)
  • Perl: 是Unix上較爲老舊的第三方腳本語言。是編程界的「瑞士軍刀」,近年被Python超越。
  • PHP: 超文本處理語言,經常使用於動態網頁編程。http://www.php.net
  • Ruby: 面向對象的愛好者和Web開發者尤爲喜歡。http://www.ruby-lang.org
  • JavaScript: 有一種實現Node.js,可執行程序是node。
  • Emacs Lisp: Lisp語言的一個變種。
  • Matlab和Octave: Matlab是一套商業矩陣及數學編程語言和庫。Octave是相似Matlab的免費軟件。
  • R: 流行的免費統計分析語言。http://www.r-project.org
  • Mathematica: 商業的數學編程語言和庫。
  • m4: 宏處理語言,常見與GNU autotools。
  • Tcl: 工具命令語言,是一種簡單的腳本語言,其擴展有圖形界面的Tk和自動化工具Expect。http://tcl.tk

6. Java

Java跟C同樣都是編譯型語言,他有更簡單的語法和強大的面向對象能力。
多用於Web應用和一些特定的應用。Android應用就一般使用Java來開發的。

Java編譯器分爲兩種:
用於生成機器碼供系統使用的本地編譯器(如C編譯器);
字節碼解釋器(有時也叫虛擬機)使用的字節碼編譯器。在Linux上看到的Java程序都是字節碼。(.class文件)

Java運行時環境(Java Runtime Environment, JRE)包含了運行Java字節碼所需的程序。運行一個字節碼:
$ java file.class
$ java -jar file.jar
(.jar)文件是由一堆.class文件打包而成的字節碼文件。

有時須要將java的安裝路徑設置到JAVA_HOME環境變量中,甚至可能還須要使CLASSPATH變量包含你程序須要的全部class文件目錄。

須要使用(Java Development Kit, JDK)Java開發工具,將.java文件編譯爲字節碼:
$ javac file.java
JDK還包含了jar程序,建立和拆分.jar文件,用法相似tar。

相關文章
相關標籤/搜索