Cmake使用總結(jié)

  • 即將步入工作,正在實(shí)習(xí)中.......
  • 感覺還是把學(xué)生時(shí)代的良好習(xí)慣帶入工作之中......
  • 博客僅在工作之外記錄,不占用任何工作時(shí)間......
  • 這里僅記錄在工作中的經(jīng)驗(yàn)之談,不涉及任何與公司相關(guān)利益,如有侵權(quán)請(qǐng)告之立馬刪除......

make/cmake/qmake

下面段話解釋來自知乎大神https://www.zhihu.com/question/27455963/answer/89770919

  • gcc是GNU Compiler Collection(就是GNU編譯器套件),也可以簡單認(rèn)為是編譯器,它可以編譯很多種編程語言(括C、C++、Objective-C、Fortran、Java等等)。
  • 當(dāng)你的程序只有一個(gè)源文件時(shí),直接就可以用gcc命令編譯它。
  • 但是當(dāng)你的程序包含很多個(gè)源文件時(shí),用gcc命令逐個(gè)去編譯時(shí),你就很容易混亂而且工作量大
  • 所以出現(xiàn)了make工具make工具可以看成是一個(gè)智能的批處理工具,它本身并沒有編譯和鏈接的功能,而是用類似于批處理的方式—通過調(diào)用makefile文件中用戶指定的命令來進(jìn)行編譯和鏈接的。
  • 5.makefile是什么?簡單的說就像一首歌的樂譜,make工具就像指揮家,指揮家根據(jù)樂譜指揮整個(gè)樂團(tuán)怎么樣演奏,make工具就根據(jù)makefile中的命令進(jìn)行編譯和鏈接的。
  • makefile命令中就包含了調(diào)用gcc(也可以是別的編譯器)去編譯某個(gè)源文件的命令。
  • makefile在一些簡單的工程完全可以人工手下,但是當(dāng)工程非常大的時(shí)候,手寫makefile也是非常麻煩的,如果換了個(gè)平臺(tái)makefile又要重新修改。
  • 這時(shí)候就出現(xiàn)了Cmake這個(gè)工具,cmake就可以更加簡單的生成makefile文件給上面那個(gè)make用。當(dāng)然cmake還有其他功能,就是可以跨平臺(tái)生成對(duì)應(yīng)平臺(tái)能用的makefile,你不用再自己去修改了。
  • 可是cmake根據(jù)什么生成makefile呢?它又要根據(jù)一個(gè)叫CMakeLists.txt文件(學(xué)名:組態(tài)檔)去生成makefile。
  • 到最后CMakeLists.txt文件誰寫???親,是你自己手寫的。
  • 當(dāng)然如果你用IDE,類似VS這些一般它都能幫你弄好了,你只需要按一下那個(gè)三角形
  • 接著是qmake,qmake是什么,先說一下Qt這個(gè)東西。Qt是跨平臺(tái)C++圖形用戶界面應(yīng)用程序開發(fā)框架。它既可以開發(fā)GUI程序,也可用于開發(fā)非GUI程序,比如控制臺(tái)工具和服務(wù)器。簡單的說就是C++的第三方庫,使用這個(gè)庫你可以很容易生成windows,Linux,MAC os等等平臺(tái)的圖形界面?,F(xiàn)在的Qt還包含了開發(fā)各種軟件一般需要用到的功能模塊(網(wǎng)絡(luò),數(shù)據(jù)庫,XML,多線程啊等等),比你直接用C++(只帶標(biāo)準(zhǔn)內(nèi)褲那種)要方便和簡單。
  • 你可以用Qt簡簡單單就實(shí)現(xiàn)非常復(fù)雜的功能,是因?yàn)镼t對(duì)C++進(jìn)行了擴(kuò)展,你寫一行代碼,Qt在背后幫你寫了幾百上千行,而這些多出來的代碼就是靠Qt專有的moc編譯器(The Meta-Object Compiler)和uic編譯器(User Interface Complier)來重新翻譯你那一行代碼。問題來了,你在進(jìn)行程序編譯前就必須先調(diào)用moc和uic對(duì)Qt源文件進(jìn)行預(yù)處理,然后再調(diào)用編譯器進(jìn)行編譯。上面說的那種普通makefile文件是不適用的,它沒辦法對(duì)qt源文件進(jìn)行預(yù)處理。所以qmake就產(chǎn)生了。
  • qmake工具就是Qt公司制造出來,用來生成Qt 專用makefile文件,這種makefile文件就能自動(dòng)智能調(diào)用moc和uic對(duì)源程序進(jìn)行預(yù)處理和編譯。qmake當(dāng)然必須也是跨平臺(tái)的,跟cmake一樣能對(duì)應(yīng)各種平臺(tái)生成對(duì)應(yīng)makefile文件。
  • qmake是根據(jù)Qt 工程文件(.pro)來生成對(duì)應(yīng)的makefile的。工程文件(.pro)相對(duì)來說比較簡單,一般工程你都可以自己手寫,但是一般都是由Qt的開發(fā)環(huán)境 Qt Creator自動(dòng)生成的,你還是只需要按下那個(gè)邪惡三角形就完事了。
  • 還沒有完,由于qmake很簡單很好用又支持跨平臺(tái),而且是可以獨(dú)立于它的IDE,所以你也可以用在非Qt工程上面,照樣可以生成普通的makefile,只要在pro文件中加入CONFIG -= qt就可以了。
  • 這樣qmake和cmake有什么區(qū)別?
  • 不好意思,cmake也是同樣支持Qt程序的,cmake也能生成針對(duì)qt 程序的那種特殊makefile, 只是cmake的CMakeLists.txt 寫起來相對(duì)與qmake的pro文件復(fù)雜點(diǎn)。 qmake 是為 Qt 量身打造的,使用起來非常方便,但是cmake功能比qmake強(qiáng)大。 一般的Qt工程你就直接使用qmake就可以了,cmake的強(qiáng)大功能一般人是用不到的。 當(dāng)你的工程非常大的時(shí)候,又有qt部分的子工程,又有其他語言的部分子工程,據(jù)說用cmake會(huì)方便,我也沒試過。
  1. make是最原始的編譯方式,執(zhí)行makefile
  2. cmake是make的升級(jí)版本,執(zhí)行CMakeLists.txt
  3. qmake是QT自有的,也算是make的升級(jí)版本,執(zhí)行.pro
  4. 平時(shí)的時(shí)候真的感覺不到編譯的重要性,現(xiàn)在到公司需要寫一些腳本,這少不了~~~
簡圖

編寫簡單cmake

makefile還是別浪費(fèi)時(shí)間了,看了一下太麻煩也沒必要,一個(gè)工具大概了解即可。

  • 一個(gè)cpp文件
//main.c
#include <stdio.h>
#include <stdlib.h>

/**
 * power - Calculate the power of number.
 * @param base: Base value.
 * @param exponent: Exponent value.
 *
 * @return base raised to the power exponent.
 */
double power(double base, int exponent)
{
    int result = base;
    int i;

    if (exponent == 0) {
        return 1;
    }
    
    for(i = 1; i < exponent; ++i){
        result = result * base;
    }

    return result;
}

int main(int argc, char *argv[])
{
    if (argc < 3){
        printf("Usage: %s base exponent \n", argv[0]);
        return 1;
    }
    double base = atof(argv[1]);
    int exponent = atoi(argv[2]);
    double result = power(base, exponent);
    printf("%g ^ %d is %g\n", base, exponent, result);
    return 0;
}
#CMakeList.txt
# CMake 最低版本號(hào)要求
cmake_minimum_required (VERSION 2.8)
# 項(xiàng)目信息
project (Demo1)
# 指定生成目標(biāo)
add_executable(Demo main.cc)

由于生成很多.o和.lib文件,最好新建一個(gè)build文件,在build文件里面運(yùn)行cmake..然后make
這樣就可以使得編譯文件和源文件分開,便于調(diào)試

  • 兩個(gè)cpp文件 + 一個(gè)h文件
//hello.h
#ifndef __HELLO__
#define __HELLO__
void hello(const char* name);
#endif //__HELLO__
#include <stdio.h>
#include "hello.h"
void hello(const char * name)
{
    printf ("Hello %s!/n", name);
}
project(HELLO)
set(SRC_LIST main.c hello.c)
add_executable(hello ${SRC_LIST})
  • 指定位置生成文件

  • 生成動(dòng)態(tài)庫文件

  • cmake參考手冊(cè)
CMake手冊(cè)的客套話總算說完了,開始進(jìn)入正題。第一部分是CMake命令。命令就相當(dāng)于命令行下操作系統(tǒng)提供的各種命令,重要性不言而喻;可以說,這些命令是CMake構(gòu)建系統(tǒng)的骨架。CMake 2.8.3共有80條命令,分別是:add_custom_command, add_custom_target, add_definitions, add_dependencies, add_executable, add_library, add_subdirectory, add_test, aux_source_directory, break, build_command, cmake_minimum_required, cmake_policy, configure_file, create_test_sourcelist, define_property, else, elseif, enable_language, enable_testing, endforeach, endfunction, endif, endmacro, endwhile, execute_process, export, file, find_file, find_library, find_package, find_path, find_program, fltk_wrap_ui, foreach, function, get_cmake_property, get_directory_property, get_filename_component, get_property, get_source_file_property, get_target_property, get_test_property, if, include, include_directories, include_external_msproject, include_regular_expression, install, link_directories, list, load_cache, load_command, macro, mark_as_advanced, math, message, option, output_required_files, project, qt_wrap_cpp, qt_wrap_ui, remove_definitions, return, separate_arguments, set, set_directory_properties, set_property, set_source_files_properties, set_target_properties, set_tests_properties, site_name, source_group, string, target_link_libraries, try_compile, try_run, unset, variable_watch, while。這些命令在手冊(cè)中是字典序排列的;為了便于查找,翻譯也按照字典序來組織。但是在翻譯結(jié)束后,會(huì)對(duì)命令進(jìn)行小結(jié),與大家討論一下這些命令的使用方法和使用時(shí)機(jī)。

用到什么就學(xué)什么,先寫幾個(gè)demo,然后直接上手做項(xiàng)目了,這是項(xiàng)目工具沒必要仔細(xì)學(xué)

參考資料

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容