C++ va CMake - abadiy birodarlar, II qism

C++ va CMake - abadiy birodarlar, II qism

Oldingi qismda Ushbu qiziqarli hikoya CMake qurish tizimi generatorida sarlavhalar kutubxonasini tashkil qilish haqida gapirdi.

Bu safar biz unga kompilyatsiya qilingan kutubxonani qo'shamiz, shuningdek modullarni bir-biri bilan bog'lash haqida gaplashamiz.

Avvalgidek, sabrsizlar darhol mumkin yangilangan omborga o'ting va o'z qo'llaringiz bilan hamma narsaga teging.


Mundarija

  1. Bo'lmoq
  2. Zabt et

Bo'lmoq

Bizning yuksak maqsadimizga erishishimiz kerak bo'lgan birinchi narsa, biz ishlab chiqayotgan dasturiy ta'minotni foydalanuvchi nuqtai nazaridan bir xil bo'lgan universal, izolyatsiya qilingan bloklarga bo'lishdir.

Birinchi qismda bunday standart blok tasvirlangan - sarlavha kutubxonasi bo'lgan loyiha. Endi loyihamizga kompilyatsiya qilingan kutubxonani qo'shamiz.

Buning uchun funktsiyani amalga oshirishni chiqaramiz myfunc alohida holatda .cpp-fayl:

diff --git a/include/mylib/myfeature.hpp b/include/mylib/myfeature.hpp
index 43db388..ba62b4f 100644
--- a/include/mylib/myfeature.hpp
+++ b/include/mylib/myfeature.hpp
@@ -46,8 +46,5 @@ namespace mylib

         ~  see mystruct
      */
-    inline bool myfunc (mystruct)
-    {
-        return true;
-    }
+    bool myfunc (mystruct);
 }
diff --git a/src/mylib/myfeature.cpp b/src/mylib/myfeature.cpp
new file mode 100644
index 0000000..abb5004
--- /dev/null
+++ b/src/mylib/myfeature.cpp
@@ -0,0 +1,9 @@
+#include <mylib/myfeature.hpp>
+
+namespace mylib
+{
+    bool myfunc (mystruct)
+    {
+        return true;
+    }
+}

Keyin biz kompilyatsiya qilinadigan kutubxonani aniqlaymiz (myfeature), oldingi bosqichda olingan narsalardan iborat bo'ladi .cpp-fayl. Yangi kutubxona, shubhasiz, mavjud sarlavhalarni talab qiladi va buni ta'minlash uchun u mavjud maqsadga bog'lanishi mumkin va kerak. mylib. Bundan tashqari, ular orasidagi aloqa ommaviydir, ya'ni maqsad bog'langan hamma narsa myfeature, yuk va maqsadni avtomatik ravishda oladi mylib (trikotaj usullari haqida ko'proq).

diff --git a/CMakeLists.txt b/CMakeLists.txt
index 108045c..0de77b8 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -64,6 +64,17 @@ target_compile_features(mylib INTERFACE cxx_std_17)

 add_library(Mylib::mylib ALIAS mylib)

+###################################################################################################
+##
+##      ΠšΠΎΠΌΠΏΠΈΠ»ΠΈΡ€ΡƒΠ΅ΠΌΠ°Ρ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠ°
+##
+###################################################################################################
+
+add_library(myfeature src/mylib/myfeature.cpp)
+target_link_libraries(myfeature PUBLIC mylib)
+
+add_library(Mylib::myfeature ALIAS myfeature)
+

Keyinchalik, yangi kutubxona tizimda o'rnatilganligiga ishonch hosil qilamiz:

@@ -72,7 +83,7 @@ add_library(Mylib::mylib ALIAS mylib)

 install(DIRECTORY include/mylib DESTINATION include)

-install(TARGETS mylib EXPORT MylibConfig)
+install(TARGETS mylib myfeature EXPORT MylibConfig)
 install(EXPORT MylibConfig NAMESPACE Mylib:: DESTINATION share/Mylib/cmake)

 include(CMakePackageConfigHelpers)

Shuni ta'kidlash kerakki, maqsadda myfeature, kelsak mylib prefiksli taxallus yaratildi Mylib::. Ularni tizimga o'rnatish uchun eksport qilishda ikkala maqsad uchun ham xuddi shunday yoziladi. Bu har qanday maqsadlar bilan bir xilda ishlashga imkon beradi bog'lash sxemasi.

Shundan so'ng, birlik testlarini yangi kutubxona bilan bog'lash qoladi (funktsiya myfunc sarlavhadan olib tashlangan, shuning uchun endi siz havola qilishingiz kerak):

diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
index 5620be4..bc1266c 100644
--- a/test/CMakeLists.txt
+++ b/test/CMakeLists.txt
@@ -4,7 +4,7 @@ add_executable(mylib-unit-tests test_main.cpp)
 target_sources(mylib-unit-tests PRIVATE mylib/myfeature.cpp)
 target_link_libraries(mylib-unit-tests
     PRIVATE
-        Mylib::mylib
+        Mylib::myfeature
         doctest::doctest
 )

Sarlavhalar (Mylib::mylib) endi siz alohida ulanishingiz shart emas, chunki yuqorida aytib o'tilganidek, ular kutubxona bilan birga avtomatik ravishda ulanadi (Mylib::myfeature).

Keling, yangi kelgan kutubxonani hisobga olgan holda qamrov o'lchovlarini ta'minlash uchun bir nechta nuanslarni qo'shamiz:

@@ -15,11 +15,16 @@ if(MYLIB_COVERAGE AND GCOVR_EXECUTABLE)
     target_compile_options(mylib-unit-tests PRIVATE --coverage)
     target_link_libraries(mylib-unit-tests PRIVATE gcov)

+    target_compile_options(myfeature PRIVATE --coverage)
+    target_link_libraries(myfeature PRIVATE gcov)
+
     add_custom_target(coverage
         COMMAND
             ${GCOVR_EXECUTABLE}
-                --root=${PROJECT_SOURCE_DIR}/include/
-                --object-directory=${CMAKE_CURRENT_BINARY_DIR}
+                --root=${PROJECT_SOURCE_DIR}/
+                --filter=${PROJECT_SOURCE_DIR}/include
+                --filter=${PROJECT_SOURCE_DIR}/src
+                --object-directory=${PROJECT_BINARY_DIR}
         DEPENDS
             check
     )

Siz ko'proq kutubxonalar, bajariladigan fayllar va boshqalarni qo'shishingiz mumkin. Loyiha doirasida ular bir-biriga qanchalik aniq bog'langanligi muhim emas. Eng muhimi, qaysi maqsadlar modulimizning interfeysi, ya'ni ular ajralib turadi.

Zabt et

Endi bizda standart blok modullari bor va biz ularni boshqarishimiz mumkin: ularni har qanday murakkablikdagi tuzilmaga aylantiramiz, ularni tizimga o'rnatamiz yoki bitta yig'ish tizimida bir-biriga bog'laymiz.

Tizimga o'rnatish

Moduldan foydalanish variantlaridan biri bizning modulimizni tizimga o'rnatishdir.

cmake --build ΠΏΡƒΡ‚ΡŒ/ΠΊ/сборочной/Π΄ΠΈΡ€Π΅ΠΊΡ‚ΠΎΡ€ΠΈΠΈ --target install

Shundan so'ng, u buyruq yordamida boshqa har qanday loyihaga ulanadi find_package.

find_package(Mylib 1.0 REQUIRED)

Submodul sifatida ulanish

Boshqa variant - bu buyruq yordamida papkani loyihamiz bilan boshqa loyihaga submodul sifatida ulash add_subdirectory.

foydalanish

Bog'lash usullari boshqacha, ammo natija bir xil. Ikkala holatda ham, bizning modulimiz yordamida loyihada maqsadlar mavjud bo'ladi Mylib::myfeature ΠΈ Mylib::mylib, masalan, quyidagi kabi ishlatilishi mumkin:

add_executable(some_executable some.cpp sources.cpp)
target_link_libraries(some_executable PRIVATE Mylib::myfeature)

Xususan, bizning holatimizda kutubxona Mylib::myfeature kutubxona bilan bog'lanish zarur bo'lganda ulanish kerak libmyfeature. Agar sarlavhalar etarli bo'lsa, kutubxonadan foydalanishga arziydi Mylib::mylib.

CMake maqsadlari qiyin bo'lishi mumkin, masalan, faqat ba'zi xususiyatlar, bog'liqliklar va hokazolarni yuborish uchun mo'ljallangan. Shu bilan birga, ular bilan ishlash xuddi shu tarzda sodir bo'ladi.

Buni olishimiz kerak edi.

Manba: www.habr.com

a Izoh qo'shish