一.安裝cmake
安裝cmake相對簡單。可以使用如下命令直接安裝cmake。不過這樣安裝的cmake版本可能比較低,如果是想用在混合編程上不建議這樣做。因爲版本比較低可能會不支持,比如想用在Android上,cmake版本要求好像最低是3.6.0如果沒有記錯的話,而下面的命令安裝的是3.4.0。建議先大致瀏覽一遍整個博客再進行安裝。同時建議先看這篇博客,編譯opencv碰到的問題。
sudo apt-get install cmake
手動安裝cmake順序:下載最新版本,或者這裏下載指定版本。在Ubuntu中下載如下圖所示版本。
解壓下載的文件,在解壓的文件中打開終端。然後執行如下命令:
./bootstrap
make
sudo make install
cmake安裝與gcc的版本有關係,目前我的gcc版本爲5.4.0嘗試安裝cmake-3.17.0版本失敗。所以我就嘗試安裝cmake-3.15.0版本,但是在make install時出現file cannot create directory: /usr/local/doc/cmake-3.14。具體如下圖:
出現安裝失敗,我沒仔細看,還以爲是cmake版本過高。所以又下載了cmake-3.14.0版本,再執行make install時還是出現上述問題。我就不得不仔細看了。其實上面都提示了需要sudo權限。所以需要使用sudo make install。
查看cmake是否安裝成功(有輸出版本號表示安裝成功):
cmake --version
CMakeList.txt一個樣例和註釋:
# 大小寫不嚴格區分
# cmake verson,指定cmake版本
cmake_minimum_required(VERSION 3.0.0)
# set():用來顯式的定義變量
set(CMAKE_POSITION_INDEPENDENT_CODE ON) # 添加-fPIC編譯,即:裝成一個動態庫(Linux爲.so擴展文件;windows爲.dll擴展文件)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra") # CMAKE_CXX_FLAGS:設置 C++ 編譯選項。後面即爲編譯的添加的內容
set(CUDA_TOOLKIT_ROOT_DIR /usr/local/cuda) # 定義cuda路徑變量
# project name,指定項目的名稱,一般和項目的文件夾名稱對應
project(smart)
add_definitions(-std=c++11) # 添加支持c++11特徵
# find_package(CUDA)
find_package(OpenCV REQUIRED) # 添加opencv依賴庫
if (NOT OpenCV_FOUND)
message(FATAL_ERROR "opencv not found")
endif (NOT OpenCV_FOUND)
set(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR}/lib)
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}/bin)
add_subdirectory(src) # 指定的文件夾加到build任務列表中
二.opencv-gpu版本的編譯
2.1添加依賴庫(最好更換成國內源)
# cmake安裝
sudo apt-get install build-essential
sudo apt-get install libgtk2.0-dev # 2.0以上的版本
sudo apt-get install pkg-config
sudo apt-get install python-dev python-numpy
sudo apt-get install libavformat-dev libavcodec-dev libswscale-dev libtbb2 libtbb-dev libjpeg-dev libpng12-dev libtiff5-dev libjasper-dev libdc1394-22-dev
如果在cmake的時候添加了如下選項:
-DWITH_OPENGL=ON
請添加如下依賴庫:
sudo apt-get install mesa-common-dev
sudo apt-get install libgl1-mesa-dev libglu1-mesa-dev
如果在上述安裝過程碰到“無法修正錯誤,因爲您要求某些軟件包保持現狀,就是它們破壞了軟件包間的依賴關係”問題,可以參考這裏。
2.2編譯opencv時參數的意義
編譯opencv的難點、重點就是編譯時參數的選擇了。不同的參數最後編譯的版本就不一樣。
參數說明,注意不同版本有的參數可能沒有或者名字更改了(參數有很多,更多參數可看這裏):
cmake \
-D CMAKE_BUILD_TYPE=RELEASE \ # 編譯opencv的版本。這裏是release版本
-D CMAKE_INSTALL_PREFIX=/usr/local \ # 爲opencv安裝的目錄,可按實際目錄進行修改,一般放在/usr/local目錄下
-D OPENCV_EXTRA_MODULES_PATH=../opencv_contrib-3.3.0/modules/ \ # 該選選項爲opencv_contrib模塊下module文件夾,按實際目錄進行修改,若不編譯opencv_contrib模塊,該選項可以省略
-D CUDA_CUDA_LIBRARY=/usr/local/cuda/lib64/stubs/libcuda.so \ # cuda的動態庫文件地址
-D CUDA_ARCH_BIN=7.5 \ # 顯卡的算力
-D CUDA_ARCH_PTX="" \ # 代表PTX代碼(反正很高級的樣子,具體可看:https://bbs.csdn.net/topics/390796227)
-D WITH_CUDA=ON \ # 編譯CUDA版本
-D WITH_TBB=ON \ # 支持高性能並行的Intel tbb(AMD?)
-D BUILD_NEW_PYTHON_SUPPORT=ON \ 支持Python 查找資料時發現有人說變成:BUILD_PYTHON_SUPPORT
-D WITH_V4L=ON \ # 增加對V4L的支持。比如用在板子對攝像頭的調用上
-D INSTALL_C_EXAMPLES=ON \ # 安裝c版本的例子(opencv3還是4已經放棄了c的維護了吧)
-D INSTALL_PYTHON_EXAMPLES=ON \ # 安裝Python版本的例子
-D BUILD_EXAMPLES=ON \ # 安裝例子
-D WITH_QT=ON \ # 添加對qt的支持
-D WITH_OPENGL=ON \ # 添加對opengl的支持
-D ENABLE_FAST_MATH=1 \ # 支持math快速計算
-D CUDA_FAST_MATH=1 \ # cuda的math快速計算
-D WITH_CUBLAS=1 \ # 支持NVidia Cuda基本線性代數子程序(BLAS)庫
-D WITH_NVCUVID=ON \ # NVidia視頻解碼庫支持
-D BUILD_opencv_cudacodec=OFF .. # cuda10已經被單獨分出了,所以用off。後面兩點是上一層目錄的意思,不可少。
2.3opencv編譯過程
如果不想編譯帶上contrib和gpu的版本,可以參考如下博客:
現在要開始編譯了。具體如下:
2.3.1準備opencv4.1.0和對應的contrib版本
解壓兩個文件,contrib文件和opencv-4.1.0同級。如下圖所示:
2.3.2準備相應安裝位置
終端進入opencv-4.1.0文件中,輸入如下命令:
mkdir build
cd build
效果如下:
2.3.3cmake編譯參數
根據自己的需求選擇參數,我選擇的參數如下。將它們輸入剛剛打開的終端(cuda10以上-DBUILD_opencv_cudacodec=OFF一定要添加,要不然會報缺失nvcuvid.h文件的錯,當然也可以去官網下載所需文件)。注意:我的添加“-DWITH_TBB=ON”選項,會出現“對‘__cxa_init_primary_exception@CXXABI_1.3.11’未定義的引用”和“對‘std::__exception_ptr::exception_ptr::exception_ptr(void*)@CXXABI_1.3.11’未定義的引用”的錯誤。
cmake -DCMAKE_BUILD_TYPE=RELEASE \
-DCMAKE_INSTALL_PREFIX=/usr/local \
-DINSTALL_PYTHON_EXAMPLES=ON \
-DOPENCV_GENERATE_PKGCONFIG=ON \
-DOPENCV_EXTRA_MODULES_PATH=../../opencv_contrib-4.1.0/modules \
-DPYTHON3_EXECUTABLE=/usr/bin/python3 \
-DPYTHON_EXECUTABLE=/usr/bin/python \
-DWITH_V4L=ON \
-DWITH_QT=ON \
-DWITH_GTK=ON \
-DWITH_OPENGL=ON \
-DWITH_CUDA=ON \
-DENABLE_FAST_MATH=ON \
-DCUDA_FAST_MATH=ON \
-DWITH_CUBLAS=ON \
-DWITH_NVCUVID=ON \
-DBUILD_opencv_cudacodec=OFF \
-DBUILD_TIFF=ON ..
編譯前效果如下圖:
編譯完成後,參數配置情況:
2.3.4make、安裝和配置環境
執行完上面的命令後,輸入如下命令(注意 -j8 表示使用8線程進行make。這一步比較耗時,多則一兩天,少的也快,半個小時,看CPU的性能。儘量用CPU最大性能):
make -j8
上面的步驟有百分比進度條,可能會出現很多的錯誤(我碰到的錯誤等下整理處理),解決了錯誤後(沒有改變cmake參數的情況),可以不從cmake開始,可以直接執行make -j8繼續執行。
沒有錯誤後進行安裝,如下:
sudo make install
配置c++,輸入如下命令:
sudo gedit /etc/ld.so.conf.d/opencv4.conf
在打開的文件的最後一行添加如下路徑:
/usr/local/lib
更新系統庫:
sudo ldconfig
添加環境變量:
sudo gedit /etc/profile
加入如下內容:
export PATH="/usr/local/lib/pkgconfig:$PATH"
刷新一下剛剛更改的文件:
sudo source /etc/profile
三.測試是否安裝成功
3.1測試程序一:常規測試
在一個沒有中文的路徑下新建一個test_opencv文件,在該文件下新建CMakeLists.txt文件和main.cpp。注意測試的opencv的版本是4.1.0,如果其他版本可能會有稍微的差別。如下:
CMakeLists.txt
# cmake needs this line
cmake_minimum_required(VERSION 2.8)
# Define project name
project(test)
# Find OpenCV, you may need to set OpenCV_DIR variable
# to the absolute path to the directory containing OpenCVConfig.cmake file
# via the command line or GUI
find_package(OpenCV REQUIRED)
set(CMAKE_CXX_STANDARD 14)
# If the package has been found, several variables will
# be set, you can find the full list with descriptions
# in the OpenCVConfig.cmake file.
# Print some message showing some of them
message(STATUS "OpenCV library status:")
message(STATUS " version: ${OpenCV_VERSION}")
message(STATUS " libraries: ${OpenCV_LIBS}")
message(STATUS " include path: ${OpenCV_INCLUDE_DIRS}")
if(CMAKE_VERSION VERSION_LESS "2.8.11")
# Add OpenCV headers location to your include paths
include_directories(${OpenCV_INCLUDE_DIRS})
endif()
# Declare the executable target built from your sources
add_executable(opencv_example main.cpp)
# Link your application with OpenCV libraries
target_link_libraries(opencv_example ${OpenCV_LIBS})
main.cpp(早期的opencv調用gpu用的是:#include "opencv2/gpu/gpu.hpp")
using namespace std;
#include "opencv2/opencv.hpp"
#include "opencv2/core/cuda.hpp"
using namespace cv;
using namespace cv::cuda;
int main()
{
int num_devices = cv::cuda::getCudaEnabledDeviceCount();
cout<<num_devices<<endl;
}
在test_opencv文件中打開終端,輸入如下命令:
cmake .
make
./opencv_example
如果opencv安裝成功,代碼編譯成功:則會顯示出1來(如果2塊顯卡就顯示2),若爲0表示安裝不成功。我的測試結果:
3.2測試程序二:使用g++打包程序
目錄如下:
main.cpp
#include<iostream>
#include<opencv2/opencv.hpp>
using namespace cv;
using namespace std;
int main()
{
Mat srcImage=imread("123.png");
imshow("Origin",srcImage);
waitKey(0);
return 0;
}
在所在文件的目錄裏打開終端,輸入如下命令(如果不帶“-DOPENCV_GENERATE_PKGCONFIG=ON”參數,下面的命令極大可能會報錯):
g++ -std=c++11 main.cpp -o main `pkg-config --cflags --libs opencv4`
執行完上面的命令後會出現一個叫“mian”的斜的正方形,如下所示:
雙擊該文件就會顯示“123.png”這個圖片,效果如下:
3.3測試程序三:調用gpu
執行這個程序可能需要添加必要的依賴庫或者其他操作,請移步這裏的第五個問題,按照測試程序一的步驟執行,如果出現相同錯誤,可以採用博客所寫方法嘗試一下。
四.卸載opencv
首先要找到當初安裝opencv的build目錄,進入該build目錄執行卸載操作(有的可能是release)。
sudo make uninstall
cd ..
rm -rf build # rm -rf release
如果這個目錄被以前被誤刪了,那麼需要重新建立build目錄並安裝對應版本,然後再執行上邊卸載步驟。然後清理/usr中所有opencv相關項(注意,opencv4.0.0以後文件的名字是opencv4)。
sudo rm -rf /usr/local/include/opencv4 /usr/local/share/opencv4 /usr/local/lib/libopencv*
cd /usr
find . -name "*opencv*" | xargs sudo rm -rf
注意,如果卸載opencv後,依賴庫最好是重新安裝一遍(最少檢查一遍)。