Linux 自動化構建工具 make/Makefile

来源:https://www.cnblogs.com/helong-123/archive/2022/06/20/16393401.html
-Advertisement-
Play Games

鏡像下載、功能變數名稱解析、時間同步請點擊 阿裡雲開源鏡像站 VS中有一鍵編譯+自動運行,Linux也給我們提供了對應的編譯方式,雖然不及VS那麼便捷,但是相比於手動輸入 gcc -o add add.c ,我們一句make就可以搞定 Makefile是一個文件,能夠存放上述 gcc -o add add. ...


鏡像下載、功能變數名稱解析、時間同步請點擊 阿裡雲開源鏡像站

VS中有一鍵編譯+自動運行,Linux也給我們提供了對應的編譯方式,雖然不及VS那麼便捷,但是相比於手動輸入 gcc -o add add.c ,我們一句make就可以搞定

Makefile是一個文件,能夠存放上述 gcc -o add add.c 這種編譯指令

make是一個命令工具,能夠解釋Makefile中的指令

要如何編譯.c文件,關鍵就在於Makefile是怎麼寫的,下麵我們主要介紹這兩者的使用

一、 單個文件的編譯

假設我們要編譯這麼一個test.c文件,我們希望編譯生成一個名為test的可執行文件

file

我們在test.c所在目錄下創建一個Makefile文件,這裡有兩種編譯寫法

1、寫法一:逐個生成.i、.s、.o文件,最後再生成 test執行文件

先一步步向下分析,需要什麼依賴文件,然後再一步步生成

file

編寫好以後,我們只需要在命令行輸入make,系統就會幫我們自動編譯了,同時會生成每一步產生的文件按

file

2、 寫法二:一步到位,直接通過 test.c 生成 test 執行文件(推薦)

Makefile中要寫的內容如下

file

第一行:確定好依賴文件和目標文件。也就是要用依賴文件來生成目標文件

第二行:編譯指令。

            [email protected] 指向第一行的目標文件,表示目標文件test

            $^ 指向第一行的依賴文件,表示依賴文件test.c

            -std 表示採用的C++標準

接下來我們只需要在命令行輸入make,系統就會幫我們編譯了,編譯成功以後,當前目錄下就會多出一個test 執行文件

file

file

3、 Makefile自動清理

我們每次開始編譯之前,我們最好先清理一下之前生成的執行文件,手動輸入 rm test 有點太麻煩了,Makefile只要寫入下麵的內容,就會自動幫我們清理了

file

如果我們還希望移除生成的.o 、.s、.i文件,那麼第6行只要換成

rm -f test test.o test.s test.i

一般我們make的時候,系統會自動調用,當然也可以手動調用,如

file

file

我們會發現之前的test執行文件不見了

二、多個文件的編譯(同一目錄下)

現在我們有三個文件,分別是test.c、sub.c、sub.h,而且我們要在test.c中調用sub.h中的函數

file

Makefile中的內容如下:

file

test執行文件 要依賴 多個文件生成的 .o文件,現在沒有 .o文件,所以需要重新生成 .o文件

當前路徑下有多個.c文件,我們逐個去寫的話,就是

test.o:test.c
    gcc -c [email protected] $^
sub.o:sub.c
    gcc -c [email protected] $^

但是這樣寫太複雜了,我們可以選擇下麵這種寫法

%.o: %.c
    gcc -c $<
  • %.o:表示目標文件是 .o文件

  • %.c:表示依賴文件是當前路徑下的 .c文件,可以看作是一個集合中放著 test.c sub.c

  • $< : 展開%.c ,逐個生成對應的 .o文件,比如test.c就會生成對應的test.o、sub.c就會生成對應的

      sub.o
    

現在我們來運行一下

file

file

三、多個文件的編譯(不同目錄下)

現在我們有三個文件,test.c、sub.h、sub.c,但是其中sub.h、sub.c在其目錄func_dir 下

file

file

Makefile的內容如下:

file

現在我們來運行一下試試

file

file

四、一次生成多個運行文件

1、常規寫法嘗試及其不可行的原因

=常規寫法嘗試=

上面的都是一個main函數文件 + 一堆函數文件的編譯,但是有的時候,比如不同進程間通信時,我們可能需要一次生成兩個運行文件,如果我們按照常規的思路來寫,會怎麼樣?

file

file

測試結果如下,我們發現只生成了一個運行文件,很顯然無法按照常規的寫法來寫

file

=原因分析=

Makefile自動構建結束會生成運行文件,預設只生成最開始的一個,我們寫的時候,server的生成放在client的前面,server就是最開始的哪一個,所以Makefile就只生成了 server

2、改進

Makefile既然生成server以後,就不會繼續生成下一個運行文件,那麼我們就要在這之前就告訴Makefile,我希望生成兩個運行文件(因為Makefile是自頂向下運行的,不會上來就去執行gcc指令)

file

然後我們再來看一下測試結果,現在就能一次生成兩個運行文件了

file

本文轉自:https://blog.csdn.net/challenglistic/article/details/124249349


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 大佬的理解->《Java IO(五) -- 字元流進階及BufferedWriter,BufferedReader》 1、BufferedReader BufferedReader高效字元流讀取文件基本用法,自帶緩衝區,讀取文件效率高,支持逐行讀取; 1.1 初始化 BufferedReader(R ...
  • 游戲的世界精彩紛呈,有動作類、策略類、角色扮演類等諸多類型,還有很多難以分類的小游戲,讓人玩起來往往愛不釋手 ...
  • 大佬的理解->《Java IO(四) -- 字元流》 FileReader字元流讀取文件,更適合用於讀取文件,可以讀取中文 1、FileReader 1.1 初始化 FileReader(File file) FileReader(String fileName) 1.2 讀取文件內容 read() ...
  • 項目全部代碼地址:https://github.com/Tom-shushu/work-study.git (mqtt-emqt 項目) 先看我們最後實現的一個效果 1.手機端向主題 topic111 發送消息,並接收。(手機測試工具名稱:MQTT調試器) 2.控制台列印 MQTT基本簡介 MQTT ...
  • 大佬的理解->《Java IO(三) -- 位元組流》 1、FileInputStream 1.1 初始化 FileInputStream(String name) FileInputStream(File file) //直接通過文件地址初始化 FileInputStream fis = new i ...
  • 第二回 巧習得元素分類 子不知懷璧其罪 雲溪父親見狀看了看雲溪,臉上滲出意思冷汗,但遲疑一下就立即退了出去,匆匆忙忙的往右邊廚房趕,只留下了雲溪和這位神秘的老爺子。 雲溪瞠目結舌的看著悠然自得的喝著老爹泡的茶的老爺子,下意識說了一句:“老先生你怎麼這麼快,還知道我要來這裡”。 “方向,你一直在繞巷子 ...
  • 一、Iproute2簡介 Iproute2是一個在Linux下的高級網路管理工具軟體。實際上,它是通過rtnetlink sockets方式動態配置內核的一些小工具組成的,從Linux2.2內核開始,Alexey Kuznetsov 實現了通過rtnetlink sockets用來配置網路協議棧,它 ...
  • 目錄 一、前景回顧 二、用C語言編寫內核 三、載入內核 四、運行測試 一、前景回顧 本回開始,我們要開始編寫內核代碼了,在此之前,先梳理一下已經完成的工作。 藍色部分是目前已經完成的部分,黃色部分是本節將要實現的。 二、用C語言編寫內核 為什麼要用C語言來編寫內核呢,其實用彙編語言也可以實現,只是對 ...
一周排行
    -Advertisement-
    Play Games
  • 什麼是工廠模式 工廠模式是最常用的設計模式之一,屬於創建型模式。 有點: 解耦,可以把對象的創建和過程分開 減少代碼量,易於維護 什麼時候用? 當一個抽象類有多個實現的時候,需要多次實例化的時候,就要考慮使用工廠模式。 比如:登錄的抽象類ILoginBusiness,它有2個實現,一個用用戶名密碼登 ...
  • 這次iNeuOS升級主要升級圖形渲染引擎和增加豐富的圖元信息,可以很快的方案應用。總共增加41個通用和行業領域的圖元應用,增加2154個圖元信息,現在iNeuOS視圖建模功能模塊總共包括5894個行業圖元信息。現在完全支持製作高保真的工藝流程和大屏展示效果。 ...
  • 效果圖先附上: 首先 這是我是參考 教程:使用 SignalR 2 和 MVC 5 實時聊天 | Microsoft Docs 先附上教程: 在“添加新項 - SignalRChat”中,選擇 InstalledVisual> C#>WebSignalR>,然後選擇 SignalR Hub 類 (v ...
  • 一、前言 項目中之前涉及到胎兒心率圖曲線的繪製,最近項目中還需要添加心電曲線和血樣曲線的繪製功能。今天就來分享一下心電曲線的繪製方式; 二、正文 1、胎兒心率曲線的繪製是通過DrawingVisual來實現的,這裡的心電曲線我也是採用差不多相同的方式來實現的,只是兩者曲線的數據有所區別。心電圖的數據 ...
  • 安裝 Redis # 首先安裝依賴gcc, 後面需要使用make編譯redis yum install gcc -y # 進入 /usr/local/src 目錄, 把源碼下載到這裡 cd /usr/local/src # 下載 redis 7.0.2 的源碼,github被牆,可以使用國內的地址 ...
  • Redis 的定義? 百度百科: Redis(Remote Dictionary Server ),即遠程字典服務,是一個開源的使用ANSI C語言編寫、支持網路、可基於記憶體亦可持久化的日誌型、Key-Value資料庫,並提供多種語言的API。 中文官網: Redis是一個開源(BSD許可),記憶體存 ...
  • 事情的起因是收到了一位網友的請求,他的java課設需要設計實現迷宮相關的程式——如標題概括。 我這邊不方便透露相關信息,就只把任務要求寫出來。 演示視頻指路👉: 基於JavaFX圖形界面的迷宮程式演示_嗶哩嗶哩_bilibili 完整代碼鏈接🔎: 網盤:https://pan.baidu.com ...
  • Python中的字典 Python中的字典是另一種可變容器模型,且可存儲任意類型對象。鍵值使用冒號分割,你可以看成是一串json。 常用方法 獲取字典中的值 dict[key] 如果key不存在會報錯,建議使用dict.get(key),不存在返回None 修改和新建字典值 dict[key]=va ...
  • 迎面走來了你的面試官,身穿格子衫,挺著啤酒肚,髮際線嚴重後移的中年男子。 手拿泡著枸杞的保溫杯,胳膊夾著MacBook,MacBook上還貼著公司標語:“加班使我快樂”。 面試官: 看你簡歷上用過MySQL,問你幾個簡單的問題吧。什麼是聚簇索引和非聚簇索引? 這個問題難不住我啊。來之前我看一下一燈M ...
  • tunm二進位協議在python上的實現 tunm是一種對標JSON的二進位協議, 支持JSON的所有類型的動態組合 支持的數據類型 基本支持的類型 "u8", "i8", "u16", "i16", "u32", "i32", "u64", "i64", "varint", "float", "s ...