• 在Ubuntu下搭建C/C++编程环境 在Ubuntu下搭建C/C++编程环境,综合起来说就是vim+gcc+gdb。其中vim用于文本编辑,gcc用于程序编译,gdb用于代码调试。 要安装编程环境,在Terminal中执行sudo apt-get ...

    在Ubuntu下搭建C/C++编程环境

    要安装编程环境,在Terminal中执行sudo apt-get install build-essential

    桌面系统的快捷键

    如果不用桌面系统,可以关闭。
    打开Terminal的快捷键是Ctrl+Alt+T,使用快捷键Ctrl+Super+Up最大化,Alt+F4关闭。
    使用快捷键Alt+Tab切换窗口。
    长按Super键(默认为Windows键),可以看到关于桌面的所有快捷键。


    Terminal的一些基本命令

    常用命令
    另一个更全一点的
    一般最常用的是cd, ls, mkdir, rmdir, cp, rm, mv, clear, pwd, shutdown.
    一般使用时只需记住常用命令,不清楚的时候用man查询。如需查看更多命令可以阅读《The Linux Command Line》(《Linux命令行大全》)。


    编辑

    不去管vim与Emacs的世纪之争,vim真的是很强大的编辑器,摆脱对图形界面的依赖,效率会有很大提高。vim有无穷尽的插件,善加选择利用,有很多针对编程的快捷功能是vs也提供不了的。
    vim的学习曲线虽然有些陡峭,但还是很值得的。
    网上有很多学习Vim的资源,推荐几本书:《Vim用户手册中文版7.3》《A Byte of Vim》《Practical Vim》,还有这个视频教程(需要翻墙)。
    使用vim,一般只需动用肌肉“记住”一些常用操作(如下表),其余功能用的时候查询即可。

    vim入门

    vim入门主要是熟练使用基本命令。最直接的学习资源是在Terminal里输入vimtutor,会有一个差不多30分钟的入门教程。
    或者学习上文提到的书籍和视频,对常见命令均有讲解。
    推荐直接从官方文档或是书籍入手,比在网上搜来搜去只鳞片爪有效率的多。四处搜索别人的学习经验,出发点是少走弯路,结果反而欲速则不达,还不如沉下心好好看完一本书。
    有几张不同角度的cheat sheet,方便查阅。作者见文末参考链接。
    vi/vim graphical cheat sheet
    中文版
    vim cheat sheet
    程序员使用
    在vim中,获得帮助的命令是:help
    如果不知道自己想查什么,可以运行:help user-manual查看整个用户手册的目录。
    如果大概知道想使用的功能而不知道具体命令,可以使用:helpgrep在整个文档中搜索相关内容。比如想了解如何查看词首,可以运行:helpgrep beginning of a word。可以使用:cnext:cprev在搜索结果间跳转。
    更多关于帮助的帮助,参看《A Byte of Vim》中Vim en:Help这一节。

    vim自定义配置

    基本操作熟练之后,多半都会开始安插件折腾自定义配置。
    自定义配置与插件包括vimrc、global plugin、filetype plugin、syntax highlighting plugin、compiler plugin。
    一般将简单配置记录在vimrc文件里,高级功能使用插件来实现。

    在Linux系统中,vimrc文件地址是$HOME/.vimrc。vim安装时自带的插件在$VIMRUNTIME/plugin/目录下。自定义插件放在$HOME/.vim/plugin/的相应子目录下,且需在vimrc文件里设置自动加载此插件。
    详细的配置与插件使用及编写请参看《A Byte of Vim》中Vim en:Plugins这一节。

    偷了个懒,在github上发现一个很棒的配置方案spf13-vim,就直接安上了。
    spf13-vim是运行在vim层之上,为方便编程,对vimrc和plugin都做了很多特殊优化配置的一个工具。
    spf13-vim。安装很容易,根据readme上的指示进行即可。
    spf13-vim例图
    安装成功后,可以打开~/.vimrc看到spf13-vim的预置配置。创建~/.vimrc.local~/.gvimrc.local进行自定义配置。
    spf13-vim已经预置了很多插件,关于这些插件的启动和使用可以看spf13-vim的介绍和这些插件自己的github页面。此处唯一提醒的一点是<leader>键在spf13-vim这里是逗号,
    我目前也在摸索中,有心得会随时更新。这是我的操作速查表

    在Quora上看到有些人并不推荐使用spf13等工具,认为会引诱你学习这个工具的配置方式,而不是真正学习vim的配置文件,使用自定义的针对自己需求的配置文件才最符合vim精神。不过对于初学者来说,我觉得spf13-vim还是很有价值的,毕竟时间这么宝贵,折腾是很累人的。


    编译运行

    gcc

    GCC(GNU Compiler Collection)是一组编译工具的总称,支持多平台、多语言源文件到可执行文件的编译与生成。其中也包括gcc(C编译器)和g++(C++编译器)。
    推荐书籍《An Introduction to GCC》。
    在GCC内部寻找帮助,使用gcc --help,如果想看gcc选项的完整列表使用gcc -v --help 2>&1 | more
    最简单的应用示例:一个hello.cpp文件。一下语句就是编译与运行。

    1
    2
    
    g++ hello.cpp hello
    ./hello
    

    gcc常用命令

    基本语法格式如下。
    对于C:gcc [options] [filenames]
    对于C++:g++ [options] [filenames]
    上述命令行按编译选项(options)指定的操作对给定的文件(filenames)进行编译处理。

    选项主要列表如下。

    选项 选项描述
    -c 只对文件进行编译和汇编,但不进行连接,生成目标文件”.o”
    -S 只对文件进行编译,但不汇编和连接
    -E 只对文件进行预处理,但不编译汇编和连接
    -g 在可执行程序中包含标准调试信息
    -o file1 [file2] 将文件file1编译成可执行文件file2
    -v 打印出编译器内部编译各过程的命令行信息和编译器的版本
    -I dir 在头文件的搜索路径列表中添加dir目录
    -L dir 在库文件的搜索路径列表中添加dir目录
    -static 强制链接静态库
    -lNAME 连接名为libNAME的库文件
    -Wall -W 开启GCC最常用的警告,GCC的warning一般格式为file:line-number:message
    -pedantic 要求严格符合ANSI标准
    -Wconversion 开启隐式类型转换警告
    -Wshadow 开启同名变量函数警告
    -Wcast-qual 开启对特性移除的cast的警告,如const
    -O(-O1) 对编译出的代码进行优化
    -O2 进行比-O高一级的优化
    -O3 产生更高级别的优化
    -Os 产生最小的可执行文件
    -pg 开启性能测试,记录每个函数的调用次数与时长
    -ftest-coverage 记录每一行被执行的次数
    -fprofile-arcs 记录每个分支语句执行的频率

    注意选项的大小写。只在最后发行版时再使用优化。即使在最后发行版也应该加上-g选项。

    几种情境

    以c++为例。
    编译单个文件为可执行文件:

    g++ -Wall -W hello.cpp -o hello

    编译多个文件为可执行文件:

    g++ -Wall -W main.cpp hello_fun.cpp -o newhello

    编译单个文件为可执行文件,连接静态库static library:

    系统默认库文件在目录/usr/lib/lib,还会自动搜索/usr/local/lib//usr/lib/
    相应的,系统默认头文件在目录,会自动搜索/usr/local/include//usr/include/
    显式指定库目录与文件,g++ -Wall -W calc.cpp /usr/lib/libm.a -o calc
    或更好的写法g++ -Wall -W -static calc.cpp -lm -o calc,连接系统自动搜索库目录里的库文件。注意g++优先使用shared library。如果找到同名.so就不会用同名.a。所以如果需要强制使用.a文件的话,应使用-static
    如果不在自动搜索的库目录,两种方法。一般使用命令行这一种。

    • 使用命令行-I添加搜索头文件的目录和-L添加搜索库文件的目录,例如g++ -Wall -W -static -I/code/test/include -I/code/another/include -I. -L/code/test/lib -L/code/another/lib -L. calc.cpp -ltest。.表示当前目录。
    • 或使用环境变量C_INCLUDE_PATH(C)或CPLUS_INCLUDE_PATH(C++)和LIBRARY_PATH。用如下语句添加搜索路径,之后就可以使用g++ -Wall -W -static calc.cpp -ltest了。
      1
      2
      3
      4
      
      CPLUS_INCLUDE_PATH = /code/test/include:/code/another/include:.:$CPLUS_INCLUDE_PATH
      export CPLUS_INCLUDE_PATH
      LIBRARY_PATH = /code/test/lib:/code/another/lib:.:$LIBRARY_PATH
      export LIBRARY_PATH
      

    编译单个文件为可执行文件,连接共享库shared library:

    如果只是用了系统默认库,g++ -Wall -W calc.cpp -lm -o calc
    除了前文系统自动搜索库文件目录之外,如果要添加其他共享库目录,必须在环境变量LD_LIBRARY_PATH中添加路径。

    1
    2
    
    LD_LIBRARY_PATH = /code/test/lib:/code/another/lib:.:$LD_LIBRARY_PATH
    export LD_LIBRARY_PATH
    

    之后可以使用g++ -Wall -W calc.cpp /usr/lib/libm.so -o calcg++ -Wall -W -I/code/test/include -I/code/another/include -I. -L/code/test/lib -L/code/another/lib -L. calc.cpp -ltest
    使用ldd calc可以查看该可执行文件依赖哪些.so。

    编译多个文件为静态库文件.a:

    将多个.o文件集合为一个静态库文件.a。其中cr表示”create and replace”。

    1
    2
    3
    
    g++ -Wall -c hello_fn.cpp
    g++ -Wall -c bye_fn.cpp
    ar cr libhello.a hello_fn.o bye_fn.o
    

    可以查看一个.a文件里包含哪些.o。使用ar t libhello.a

    编译多个文件为共享库文件.so:

    g++ x.cpp y.cpp z.cpp -fPIC -shared -o libtest.so。其中-fPIC表示编译为位置独立的代码。

    预处理

    可以用gcc选项定义宏,-DNAME会定义一个名为NAME的宏。如g++ -Wall -DTEST dtest.cpp,定义了名为TEST的宏。定义的宏会对代码产生影响。
    也可以为宏定义值,-DNAME=VALUE。如g++ -Wall -DNUM=100 dtestval.cppg++ -Wall -DNUM="2+2" dtestval.cppg++ -Wall -DMESSAGE="\"Hello,World!\"" dteststr.cpp。在代码中把宏用括号括起来是好习惯。

    性能

    开启-pg选项生成可执行文件后。首先正常运行一次可执行文件./hello,然后运行gprof hello查看数据。
    开启-fprofile-arcs -ftest-coverage选项生成可执行文件后。首先正常运行一次可执行文件./hello,然后运行gcov hello.cpp查看数据。未被执行的语句会在.gcov文件中标记上-,可以通过执行grep '-' *.gcov查找未被执行的语句。

    makefile文件

    对于较大的工程,如果还像前文一样写命令行就太痛苦了。而使用makefile可以管理整个工程的编译规则,之后用一个make命令就可自动编译,相对方便很多。

    推荐书籍《跟我一起写Makefile》和官方文档。内容看起来还是很晦涩…(・-・*)还好现在有了自动化工具,用来自动生成的工具也可以用工具自动生成了。

    最基础的用法

    makefile基本规则是:

    target1 target2 target3: prerequisite1 prerequisite2
    command1
    command2

    其中target是目标文件。prerequisites是要生成target所需文件或目标。command是make需要执行的命令。规则表示了一个文件的依赖关系,即target依赖于prerequisites,生成规则为command。如果target不存在或prerequisites中至少一个文件比target新的话,command定义的命令就会执行。这就是makefile中最核心的内容。

    make工作的流程是:
    当我们输入make命令之后,

    1. 读入所有的makefile文件。
    2. 读入被include包括的其他makefile文件。
    3. 初始化文件中的变量。
    4. 推导隐式规则,分析所有规则。
    5. 为所有的目标文件创建依赖关系链。
    6. 根据依赖关系,决定哪些目标要重新生成。
    7. 执行生成命令。

    makefile文件名应为Makefilemakefile

    小示例

    我为自己刷题的一个小项目写了一个将几个目录下所有的源文件一起编译的一个makefile。在这里看工程的目录结构

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    
    EXEC = MyLeetCode
    SRC_DIR = ../../catch ../../include ../../src
    SOURCES := $(foreach x, ${SRC_DIR},\
    	$(wildcard \
    	$(addprefix ${x}/*,.cpp)))
    OBJECTS = $(SOURCES:.cpp=.o)
    CXX = g++
    CXXFLAGS = -I../../catch -I../../include -I../../src -std=c++11
    $(EXEC): $(OBJECTS)
    	$(CXX) -o $@ $^
    .PHONY : clean
    clean:
    	$(RM) $(OBJECTS)
    	$(RM) $(EXEC)
    

    网上看到一个Generic Makefile for C/C++ Program

    使用CMake自动生成makefile

    当处理较大型的项目时,手动书写makefile就比较痛苦,这时用来用来自动化自动化工具makefile的自动化工具就是CMake。不过天下哪有那么便宜的事,它也是要写自己的CMakeLists.txt的。
    推荐书籍《CMake实践》《Mastering CMake》和官网帮助

    简介

    CMake是一个跨平台的自动化建构系统,它是用一个名为CMakeLists.txt的文件来描述构建过程,可以产生标准的构建文件,如Unix的makefile或Windows Visual Studio的projects/workspaces。
    文件CMakeLists.txt需要手工编写,也可以通过编写脚本进行半自动的生成。

    在Linux平台下使用CMake生成makefile并编译的流程如下:

    1. 安装CMake。在Ubuntu上安装cmake很简单$sudo apt-get install cmake。如果想要其Qt图形界面另需安装sudo apt-get install cmake-qt-gui。一般不需要,在Ubuntu系统上用ccmake就可以了。
    2. 编写CMakeLists.txt。
    3. 运行CMake。用cd将当前目录设为生成目标目录,执行命令ccmake srcdir(文字界面)或cmake -i(交互命令行),如果想使用Qt图形界面使用cmake-gui
    4. Makefile已经生成。使用make命令进行编译。
    5. 如果想清理工程。使用make clean

    简单语法
    注释:#
    命令语法:COMMAND(参数1 参数2 ...)
    字符串列表:A;B;CA B C。分号或空格分隔的值。
    变量(字符串或字符串列表):

    set(Foo a b c)设置变量Foo。
    command(${Foo})等价于command(a b c)
    command("${Foo}")等价于command("a b c")
    command("/${Foo}")转义,和a b c无关联。

    流控制结构:

    IF()...ELSE()/ELSEIF()...ENDIF()
    WHILE()...ENDWHILE()
    FOREACH()...ENDFOREACH()

    正则表达式:

    常用命令总结

    命令 意义
    INCLUDE_DIRECTORIES( “dir1” “dir2” … ) 头文件路径,相当于编译器参数 -Idir1 -Idir2
    AUX_SOURCE_DIRECTORY( “sourcedir” variable) 收集目录中的文件名并赋值给变量
    ADD_EXECUTABLE 可执行程序目标
    ADD_LIBRARY 库目标
    ADD_CUSTOM_TARGET 自定义目标
    ADD_DEPENDENCIES( target1 t2 t3 ) 目标target1依赖于t2 t3
    ADD_DEFINITIONS( “-Wall -ansi”) 本意是供设置 -D… /D… 等编译预处理需要的宏定义参数,对比 REMOVE_DEFINITIONS()
    TARGET_LINK_LIBRARIES( target-name lib1 lib2 …) 设置单个目标需要链接的库
    LINK_LIBRARIES( lib1 lib2 …) 设置所有目标需要链接的库
    SET_TARGET_PROPERTIES( … ) 设置目标的属性 OUTPUT_NAME, VERSION, ….
    MESSAGE(…) 这个指令用于向终端输出用户定义的信息
    INSTALL( FILES “f1” “f2”DESTINATION . ) DESTINATION 相对于 ${CMAKE_INSTALL_PREFIX}
    SET( VAR value [CACHE TYPE DOCSTRING [FORCE]]) 定义与修改变量
    LIST( APPEND/INSERT/LENGTH/GET/REMOVE_ITEM/REMOVE_AT/SORT …) 列表操作
    STRING( TOUPPER/TOLOWER/LENGTH/SUBSTRING/REPLACE/REGEX …) 字符串操作
    SEPARATE_ARGUMENTS( VAR ) 转换空格分隔的字符串到列表
    FILE( WRITE/READ/APPEND/GLOB/GLOB_RECURSE/REMOVE/MAKE_DIRECTORY …) 文件操作
    FIND_FILE 注意 CMAKE_INCLUDE_PATH
    FIND_PATH 注意 CMAKE_INCLUDE_PATH
    FIND_LIBRARY 注意 CMAKE_LIBRARY_PATH
    FIND_PROGRAM  
    FIND_PACKAGE 注意 CMAKE_MODULE_PATH
    EXEC_PROGRAM( bin [work_dir] ARGS <..> [OUTPUT_VARIABLE var] [RETURN_VALUE var] ) 执行外部程序
    OPTION( OPTION_VAR “description” [initial value] )

    变量
    工程路径

    CMAKE_SOURCE_DIR PROJECT_SOURCE_DIR <projectname>_SOURCE_DIR表示工程顶层目录。
    CMAKE_BINARY_DIR PROJECT_BINARY_DIR <projectname>_BINARY_DIR表示生成目标目录。
    CMAKE_CURRENT_SOURCE_DIR表示当前处理的CMakeLists.txt所在的目录。
    CMAKE_CURRRENT_BINARY_DIR表示当前处理的CMakeLists.txt的目标目录。
    CMAKE_CURRENT_LIST_FILE输出调用这个变量的CMakeLists.txt的完整路径。

    Debug和Release模式的构建

    在CMakeList.txt文件中使用SET(CMAKE_BUILD_TYPE Debug)
    或命令行参数cmake DCMAKE_BUILD_TYPE=Release

    编译器参数

    CMAKE_C_FLAGS CMAKE_CXX_FLAGS
    也可以通过指令ADD_DEFINITIONS()添加。

    包含路径

    CMAKE_INCLUDE_PATH配合FIND_FILE()以及FIND_PATH()使用。如果头文件没有存放在常规路径(/usr/include, /usr/local/include等),则可以通过这些变量就行弥补。如果不使用FIND_FILEFIND_PATH的话,CMAKE_INCLUDE_PATH没有任何作用。
    CMAKE_LIBRARY_PATH配合配合FIND_LIBRARY()使用。否则没有任何作用。
    CMAKE_MODULE_PATHCMake为上百个软件包提供了查找器(finder):FindXXXX.cmake。当使用非CMake自带的finder时,需要指定finder的路径,这就是CMAKE_MODULE_PATH,配合FIND_PACKAGE()使用。

    编写CMakeLists.txt的示例

    对于如下的目录结构。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    
    +example
    |
    +--- CMakeList.txt
    +--+ src/
    |  |
    |  +--- main.cpp
    |  /--- CMakeList.txt
    |
    +--+ thirdparty/
    |  |
    |  +--- hello.h
    |  +--- hello.cpp
    |  /--- CMakeList.txt
    |
    /--+ build/
    

    多文件夹编译(手动)

    将所有子文件夹中的源文件包含进来,然后生成。

    在顶文件夹中example的CMakeLists.txt中:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    
    cmake_minimum_required(VERSION 2.6)
    project(HELLO)
    # include src
    include(src/CMakeLists.txt)
    foreach(FILE ${FILES})
        set(subdir1Files ${subdir1Files} src/${FILE})
    endforeach(FILE)
    # include thirdparty
    include(thirdparty/CMakeLists.txt)
    foreach(FILE ${FILES})
        set(subdir2Files ${subdir2Files} thirdparty/${FILE})
    endforeach(FILE)
    # add the source files to the executable
    add_executable(hello ${subdir1Files} ${subdir2Files})
    

    在src目录的CMakeLists.txt中:

    1
    2
    
    # list the source files for this directory
    set (FILES main.cpp)
    

    在thirdparty目录的CMakeLists.txt中:

    1
    2
    
    # list the source files for this directory
    set(FILES hello.h hello.cpp)
    

    多文件夹编译(自动)

    和上一种方式一样,只不过是自动包含。

    在顶文件夹中example的CMakeLists.txt中:

    1
    2
    3
    4
    5
    
    cmake_minimum_required(VERSION 2.6)
    project(HELLO)
    AUX_SOURCE_DIRECTORY(./thirdparty subdir1Files)
    AUX_SOURCE_DIRECTORY(./src subdir2Files)
    add_executable(hello ${subdir1Files} ${subdir2Files})
    

    另一种多文件夹编译(自动)

    也是将所有子文件夹中符合后缀的文件自动包含进来,然后生成。

    在顶文件夹example中的CMakeLists.txt中:

    1
    2
    3
    4
    5
    6
    
    cmake_minimum_required(VERSION 2.6)
    FILE(GLOB_RECURSE SRC_LIST "${PROJECT_SOURCE_DIR}/thirdparty/*.cpp" "${PROJECT_SOURCE_DIR}/src/*.cpp")
    FOREACH(src ${SRC_LIST})
        MESSAGE(${src})
    ENDFOREACH()
    add_executable(hello ${SRC_LIST})
    

    多文件夹使用静态库

    将thirdparty中的文件编译为一个静态库,由src中的另一个源文件在生成可执行文件时调用。

    在顶文件夹中example的CMakeLists.txt中:

    1
    2
    3
    4
    
    cmake_minimum_required(VERSION 2.6)
    project(HELLO)
    add_subdirectory(src)
    add_subdirectory(thirdparty)
    

    在src目录的CMakeLists.txt中:

    1
    2
    3
    4
    5
    
    #include_directories(${PROJECT_SOURCE_DIR}/thirdparty)
    set(APP_SRC main.cpp)
    set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}/bin)
    add_executable(hello ${APP_SRC})
    target_link_libraries(hello hi)
    

    在thirdparty目录的CMakeLists.txt中:

    1
    2
    3
    4
    
    set(LIB_SRC hello.cpp)
    add_library(hi ${LIB_SRC})
    set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/lib)
    set_target_properties(hi PROPERTIES OUTPUT_NAME "hi")
    

    多文件夹使用动态库

    将thirdparty中的文件编译为一个动态库,由src中的另一个源文件在生成可执行文件时调用。
    与之前静态库的区别是add_library时的参数,和兼顾平台的部分。

    thirdparty目录中的hello.h文件添加WIN32平台的导入导出设置:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    
    #include <iostream>
    #include <string>
    using namespace std;
    #if defined _WIN32
        #if LIBBUILD
            #define LIBHI_API __declspec(dllexport)
        #else
            #define LIBHI_API __declspec(dllimport)
        #endif
    #else
        #define LIBHI_API
    #endif
    LIBHI_API void say_hello(string str);
    

    在thirdparty目录的CMakeLists.txt中:

    1
    2
    3
    4
    5
    
    set(LIB_SRC hello.cpp)
    add_definitions("-DLIBBUILD")
    add_library(hi SHARED ${LIB_SRC})
    set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/lib)
    set_target_properties(hi PROPERTIES OUTPUT_NAME "hi")
    

    查找并使用其他程序库 为VS生成debug和release版

    使用CMAKE_CXX_FLAGS_DEBUGCMAKE_CXX_FLAGS_RELEASE

    以上文“多文件夹编译(自动)”为例,顶文件夹中example的CMakeLists.txt修改为:

    1
    2
    3
    4
    5
    6
    7
    
    cmake_minimum_required(VERSION 2.6)
    project(HELLO)
    SET(CMAKE_CXX_FLAGS_DEBUG "$ENV{CXXFLAGS} -O0 -Wall -g -ggdb")
    SET(CMAKE_CXX_FLAGS_RELEASE "$ENV{CXXFLAGS} -O3 -Wall")
    AUX_SOURCE_DIRECTORY(./thirdparty subdir1Files)
    AUX_SOURCE_DIRECTORY(./src subdir2Files)
    add_executable(hello ${subdir1Files} ${subdir2Files})
    

    在用ccmake生成时,图形界面会出现CMAKE_BUILD_TYPE的选项。根据不同选择会生成不同结果。


    调试

    gdb

    gdb是一个用来调试C和C++程序的功能强大的调试器,能在程序运行时观察程序的内部结构和内存使用情况。
    gdb主要提供以下功能:

    • 监视程序中变量的值的变化。
    • 设置断点,使程序在指定的代码行上暂停执行,便于观察。
    • 单步执行代码。
    • 分析崩溃程序产生的core文件。

    推荐书籍《Debugging with GDB》[在线][下载pdf]。通过在gdb下输入help或在命令行上输入gdb h查看关于gdb选项说明的简单列表。键入help后跟命令的分类名。可以获得该类命令的详细清单。搜索和word相关的命令可用apropos word

    为使gdb能正常工作,必须在程序编译时包含调试信息。即-g选项。前文有讲解。

    简单的调试步骤示例

    1. 载入test可执行文件gdb test --silent
    2. 运行run
    3. 查看程序出错的地方where
    4. 查看出错函数附近的代码list
    5. 打开堆栈backtrace
    6. 单步调节nextstep
    7. 查看可疑表达式值print var
    8. 在可疑行打断点break 8
    9. 重新运行会在断点处停止。用set variable修改变量值。
    10. 继续运行continue。看结果是否正确。
    11. 退出gdbquit

    常用命令介绍

    常用命令

    Valgrind

    Valgrind是一个工具集,其中最著名的就是可以检查内存泄露的Memcheck。
    在ubuntu上安装Valgrind的命令sudo apt-get install valgrind
    与gdb的要求相同,程序编译时需要有-g参数。
    对于平时用myprog arg1 arg2启动的可执行文件,使用valgrind --leak-check=yes myprog arg1 arg2就可以开启内存检查,如果有错误会输出。

    Valgrind命令的一般格式为valgrind [valgrind-options] your-prog [your-prog-options]
    --tool=<toolname>可以选择当前运行的工具,默认即为memcheck。
    --help显示帮助。


    [1] http://www.viemu.com/
    [2] http://bbs.zol.com.cn/diybbs/d34450_19858.html
    [3] http://4gamers.cn/blog/2014/06/19/make-your-vim-weapon/
    [4] http://derekwyatt.org/vim/tutorials/
    [5] http://www.phecda.org
    [6] http://blog.vgod.tw/tag/mit/?variant=zh-cn
    [7] http://vim.spf13.com/#vimrc
    [8] http://ram.kossboss.com/spf13c/
    [9] A Byte of Vim
    [10] http://michael.peopleofhonoronly.com/vim/
    [11] Linux环境编程
    [12] Linux C编程一站式学习
    [13] Linux环境下C编程指南
    [14] An Introduction to GCC
    [15] 跟我一起写Makefile
    [16] Mastering CMake
    [17] http://www.ibm.com/developerworks/cn/linux/l-cn-cmake/
    [18] http://blog.sina.com.cn/s/blog_9ce5a1b501015avz.html
    [19] http://blog.csdn.net/dbzhang800/article/details/6314073
    [20] http://blog.csdn.net/dbzhang800/article/details/6329068
    [21] 用GDB调试程序
    [22] GDB调试命令手册
    [23] Debugging with GDB
    [24] http://www.vingel.com/tools/reference/gdb-commands-list.png
    [25] https://wiki.ubuntu.com/Valgrind
    [26] http://valgrind.org/docs/manual/quick-start.html
    [27] http://valgrind.org/docs/manual/manual.html

    展开全文
  • Linux下的编程环境(一) 2018-06-26 12:24:04
    GCC(GNU Compiler Collection,GNU编译器套件):是由GNU开发的编程语言编译器。GCC编译器套件支持多种语言的编译,包括了C、C++、Objective-C、Fortran、Java、Ada和Go语言的前端,也包括了这些语言的库。下面表格...
  • linux下C++编程环境搭建 2018-07-28 09:27:58
    安装g++环境 安装两个RPM包即可搞定 [root@localhost Desktop]# rpm -ivh /home/weiwei/Desktop/libstdc++-devel-4.4.5-6.el6.i686.rpm [root@localhost Desktop]# rpm -ivh /home/weiwei/Desktop/gcc-c++-4.4.5...
  • 第一次安装和使用Ubuntu操作系统的读者,可能会被繁杂的安装步骤困扰,那么,笔者在网盘中共享出已经安装好的Ubuntu 10虚拟机系统。读者可以直接下载,开机使用。网盘地址如下: ... 下载后,解压得到文件夹ubuntu10...
  • 熟悉LINUX基本命令及编程环境
  • Linux编程环境搭建Linux 2010-09-15 18:23:00
    Linux编程环境搭建 对于一个经常在Linux下工作的程序员来说搭建一个好的工作环境是我们有一个好的工作效率的基础。这里以Ubuntu 10.04为例,在这里给大家总结一下,有不对的地方或者不全的地方希望大家提出,能...
  •  作者已经基于ubuntu10版本安装好了一个虚拟机系统,并且默认安装了gcc、g++和sqlite3等学习编程和编译项目使用到的工具。为了方便读者快速获取到一个完善的开发环境。创建包的ubuntu10虚拟机系统存放在网盘中,...
  • linux下c/c++编程环境搭建 2015-06-05 10:18:10
    本人想学习一下Linux下的C,C++程序开发,这几天一直在研究Linux下的C语言编译环境的建立,因为新装好的Ubuntu里面缺少函数库文件,所以无法编译最简单的C语言文件,故要先配置一番,这几天也有一点心得,写下来和...
  •  Ubuntu是非常流行的Linux操作系统,网络上提供了大量的资源,可以从官方网下载IOS安装镜像文件,官方网地址是: http://releases.ubuntu.com/releases/  进入官方网,可以看到提供了多个版本的Ubunt...
  • linux编程环境 2017-04-03 15:04:59
    而在使用Linux进行C/C++编程中,这些功能是由vim,gcc,make,gdb四个软件提供支持(也有其他变种)。 使用Linux环境的优势在于一方面在于自由,给开发者进行私人订制的空间,另一方面也是要求使用者对自己的程序负责任...
  • 如何才能成为一个Linux编程高手?在这里笔者建议大家多读经典书籍,多读优秀的开源代码,多写代码,除了这些别无它法。接下来本文就向大家推荐一些公认的Linux编程经典图书。想要成为真正的Linux编程高手,这些书籍...
  • "一个真正的程序员是不用IDE(译者注:集成开发环境)的,他们都是用带着某某插件的文本编辑器来写代码。"我们总能在某些地方听到此类观点。然 而,尽管越来越多的人同意这样的观点,但是一个IDE仍然非常有用,它...
  • 熟悉Linux编程环境,加强对Linux命令的理解及函数的运用 二.设计内容 1. 在Linux环境下模拟实现简单命令解释器。 (1)要求实现的基本命令包括: pwd //显示当前所在目录的路径名 list <目录名> //列出...
  • Linux开发环境配置 2016-11-24 11:15:52
    一、学习Linux开发的必要性 现在大部分的公司都改用Linux,尤其是银行。可见Linux是相对windows是安全的多。windows不是开源的,也就是你不知道它的源代码,我们无法或者很难在windows下面创建管理员用户,以管理员...
  • 学习UC编程时可能会遇到需要在linux系统中进行编程,但自己电脑上已经安装了win7,由于种种原因不方便重新再安装linux的问题,这时考虑使用虚拟机来进行学习无疑是最方便快捷的了,现将具体步骤整理如下: ...
  • 嵌入式Linux C编程基础 2019-07-01 10:36:46
    本课程是全套课程的第0.2.3课(预科第三课程),主题linux系统下C语言开发学习,总共25小时左右的课程。该视频是我在联嵌科技代课期间随堂真实录制,学生均为根本没接触过C语言的应届毕业生(现在全部毕业,从事...
  • 本课程讲解Linux编程下C语言的基础编程知识,包括环境构建,Linux shell命令 ,Linux VI编辑器,Linux GCC编译器使用,C语言保留字,变量,表达式、语句、函数、程序的结构、数据结构与算法、链表与栈。
  • VS2017搭建linux开发环境 2019-03-14 17:39:53
    vs2017搭与传统vs2017上的windows编程不同的是,vs2017 所需要的Linux环境需要搭载在一个linux的服务器上,vs 2017 相当于将windows系统和这个linux系统之间建立了某种映射,可以将代码拷贝到linux中对应的目录中,...
  • 憋说了,整一套吧!...提前备好Linux编程实验环境非常重要,建议人手一套,这样以后每当学完一个理论知识需要实践时,立马就可以拿到上面去练手了。 因此本文先把环境给搭建起来! 软件准备 VMwa...
  • PS:最新版的win10内嵌了Linux子系统,默认是关闭的,在这个Linux子系统上能跑一些bash东西,至于具体到什么程度,还请自己去探索,这里不作讨论,我用的是win7. 先说个前提吧,就是我用的是win7,硬盘快满了,不...
1 2 3 4 5 ... 20
收藏数 242,355
精华内容 96,942