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

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 人文社科 > 生活经验 >内容正文

生活经验

程序的编译和链接过程

發(fā)布時(shí)間:2023/11/27 生活经验 26 豆豆
生活随笔 收集整理的這篇文章主要介紹了 程序的编译和链接过程 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
一.虛擬機(jī)、linux簡介 簡單介紹一下虛擬機(jī)還有就是各種操作系統(tǒng),比如centos,Ubuntu 操作系統(tǒng):linux(centos、Ubuntu、redhat),Android,Windows(xp、win8、win10) 進(jìn)程,多個(gè)程序,分時(shí)技術(shù),并行技術(shù) 一次打開多個(gè)程序,我們?cè)谥挥幸粋€(gè)cpu,如何讓這些程序進(jìn)行執(zhí)行呢,看起來好像是在同時(shí)進(jìn)行的,實(shí)際上是一個(gè)程序執(zhí)行了一點(diǎn)點(diǎn)時(shí)間,然后保存執(zhí)行的一些信息,接下來回來再次執(zhí)行,這樣就達(dá)到了看上去是多個(gè)程序在同時(shí)執(zhí)行的效果 操作系統(tǒng)的作用:控制程序的執(zhí)行,管理系統(tǒng)的資源
二.程序的編譯鏈接過程
2.1首先看一下預(yù)處理的指令

關(guān)于上面的預(yù)處理指令,大家可以自己測試一下
(測試?yán)?#xff09;(注意是兩行) ANSI 標(biāo)準(zhǔn) C 定義的幾個(gè)宏如下,大家可以簡單的了解一下 __LINE__ 表示正在編譯的文件的行號(hào) __FILE__ 表示正在編譯的文件的名字 __DATE__ 表示編譯時(shí)刻的日期字符串,例如: "25 Dec 2007" __TIME__ 表示編譯時(shí)刻的時(shí)間字符串,例如: "12:30:55" __STDC__ 判斷該文件是不是定義成標(biāo)準(zhǔn) C 程序
2.2宏定義 編譯器在預(yù)處理的時(shí)候,就會(huì)把宏定義的數(shù)據(jù)替換成它的元身,這里我們必須了解什么是宏,宏的主要的用法 2.2.1 定義宏常量 #define PI 3.14159265358979323846264338327 比如我們經(jīng)常使用的一個(gè)變量,如果這個(gè)變量的數(shù)值改變了之后,我們不需要再文件里面一個(gè)一個(gè)找,而是只需要把宏改變就可以了 #define ERROR_TEST -1 比如我們?cè)趖est文件中,一些代碼的地方需要使用return -1,或者是exit(-1) 然后有很多類型的錯(cuò)誤返回,如果每次返回的是-1,-2,-3之類的,一會(huì)就把自己給繞暈了 2.2.2定義字符串常量 #define PATH "c/file/linux" 這個(gè)一般用在表示文件的路徑的情況下有很多 (大家下去看一下,如果是一行寫不下怎么辦呢,就是比如一行太長了怎么辦) 2.2.3 定義注釋 #define ZZ // 因?yàn)樵诔绦蚓幾g的時(shí)候,注釋是先于宏處理的 2.2.4 定義表達(dá)式(宏函數(shù)) #define MUL(x) x*x 純文本替換 測試用例 MUL(5);MUL(1+2); --- 加上括號(hào)MUL((x)*(x)) MUL(5*3)*MUL(5*3) --- 大括號(hào)???不要吝嗇括號(hào) 2.2.5 空格 #define MUL (x) ((x)*(x)) 比如上面的宏函數(shù),我們要是定義成下面的這個(gè)樣子又是什么樣的呢 2.2.6#undef 撤銷宏定義 比如 #define PI 3.14159265358979323846264338327 ... ... ... #undef PI此時(shí)PI不在有效了 2.2.7定義宏函數(shù)補(bǔ)充 比如下面的程序 #define PRINTF printf("測試");
這個(gè)時(shí)候我們可以編寫 一個(gè)if esle語句 if(0) PRINTF; else printf("haha\n");
宏函數(shù)比普通函數(shù)的一些特性在哪里 (1)普通的函數(shù)需要建立棧幀,開銷較大,宏函數(shù)在效率上面更勝一籌 (2)函數(shù)中的參數(shù)必須使用特定的類型,換句話說,宏函數(shù)對(duì)參數(shù)是不進(jìn)行類型檢查的,宏函數(shù)是不類型限制的
宏函數(shù)的缺點(diǎn) 宏函數(shù)每次是進(jìn)行的代碼的替換,有時(shí)候可能會(huì)增加代碼的長度,使維護(hù)起來非常的復(fù)雜 宏函數(shù)的參數(shù)不能是一個(gè)類型
2.3. 條件編譯 第一種形式: #ifdef 標(biāo)識(shí)符 程序段 1 #else 程序段 2 #endif 它的功能是,如果標(biāo)識(shí)符已被 #define 命令定義過則對(duì)程序段 1 進(jìn)行編譯;否則對(duì)程序段 2 進(jìn)行編譯。
第二種形式 #ifndef 標(biāo)識(shí)符程序段 1 #else 程序段 2 #endif
第三種形式 #if 常量表達(dá)式 程序段 1 #else 程序段 2 #endif

2.4. 文件包含 文件包含是預(yù)處理的一個(gè)重要功能,它可用來把多個(gè)源文件連接成一個(gè)源文件進(jìn)行編譯,結(jié)果將生成一個(gè)目標(biāo)文件。C語言提供#include 命令來實(shí)現(xiàn)文件包含的操作,它實(shí)際是宏替換的延伸,有兩種格式: #include<filename> #include"filename" 2.5.#pragma 預(yù)處理 自己上網(wǎng)調(diào)研,寫博客,寫測試用例 #pragma once #pragma warning #pragma pack--這個(gè)是張晨亮學(xué)長給你們講過的,設(shè)置內(nèi)置內(nèi)存對(duì)齊數(shù)

2.6詳解程序編譯和鏈接過程 程序的編譯和鏈接的過程 我們?cè)趌inux下使用gcc編譯器直接對(duì)程序進(jìn)行編譯,比如使用gcc test.c,然后就會(huì)生成一個(gè)程序叫做test.out 但是上面的看似簡單的過程實(shí)際上是經(jīng)歷了四個(gè)階段 預(yù)處理,編譯,匯編,連接 每個(gè)過程都有自己要完成的任務(wù)



記住一些操作,ESc對(duì)應(yīng)的是iso,
2.6.1. 預(yù)處理 通過預(yù)處理生成一個(gè).i的文件,使用的指令是 gcc -E test.c -o test.i (G) 預(yù)處理過程主要處理的是1. 以#開始的預(yù)處理指令(保留#pragma)2.刪除所有的注釋3.添加文件名和行號(hào),具體的過程如下
  • 將所有的#define刪除,展開所有的宏定義
  • 處理所有的條件預(yù)編譯指令,比如#if,#ifdef....
  • 處理所有的#include預(yù)編譯指令,將所有被包含的文件包含至本文件中來
  • 刪除所有的注釋,//和/* */等
  • 保留所有的#pragma預(yù)處理指令,因?yàn)橄旅孢€要用到它
2.6.2.編譯 gcc -S test.i -o test.s 作用:將預(yù)處理后的文件,進(jìn)行一系列的詞法分析,語法分析,語義分析及優(yōu)化后生成相應(yīng)的匯編代碼(這里我們就可以寫一個(gè)錯(cuò)誤的語句來示范一下) 2.6.3. 匯編 gcc -c test.s -o test.o 將匯編代碼解釋成編譯器可以執(zhí)行的二進(jìn)制代碼 :%!xxd 2.6.4. 鏈接 gcc -o test.o test 這里我們有一個(gè)疑問,不是說上面的匯編已經(jīng)將程序變成了二進(jìn)制代碼了,為什么還要鏈接呢,鏈接是咋鏈接呢,和誰戀呢,戀啥呢 講述一下編寫程序發(fā)展的歷史,一開始是程序員是機(jī)器碼,就是一個(gè)一個(gè)的紙條上面的01代碼,但是這種代碼太晦澀難懂了,于是出現(xiàn)了匯編語言,匯編語言出現(xiàn)之后的一個(gè)很大的問題就是,代碼的數(shù)量大大的增加了,這就使得維護(hù)代碼起來比較復(fù)雜,于是人們?yōu)榱吮阌诰S護(hù),又想起把代碼分成不同的模塊,每個(gè)模塊負(fù)責(zé)不同的作用,就比如一個(gè)頭文件是專門處理圖片的,一個(gè)頭文件是專門處理音頻,這樣就產(chǎn)生了不同的模塊,這些模塊之間存在著不同的調(diào)用的過程,然后就是要把不同的分開的模塊組裝起來就是鏈接的過程。 人們將每個(gè)源代碼模塊獨(dú)立的編譯,然后將編譯后的模塊按照他們的需求組裝起來就是鏈接的過程。 發(fā)給大家一篇PDF《靜態(tài)庫和動(dòng)態(tài)庫》

推薦書目:《程序員的自我修養(yǎng)--鏈接、裝載與庫》 《C語言深度剖析》

























總結(jié)

以上是生活随笔為你收集整理的程序的编译和链接过程的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。