dbg(…) มาโครสำหรับแฟนดีบักสไตล์ printf
ดีบักเกอร์นั้นยอดเยี่ยมมาก แต่บางครั้งคุณก็ไม่มีเวลาหรือความอดทนในการตั้งค่าทุกอย่างถูกต้อง และเพียงต้องการวิธีที่รวดเร็วในการตรวจสอบค่าบางค่าในขณะรันไทม์
โปรเจ็กต์นี้จัดเตรียมไฟล์ส่วนหัวเดี่ยวพร้อมมาโคร dbg(…) ที่สามารถใช้ได้ในทุกสถานการณ์ที่โดยทั่วไปคุณจะเขียน printf("…", …) หรือ std::cout << … แต่มันมาพร้อมกับความพิเศษบางอย่าง
# include < dbg.h >
# include < cstdint >
# include < vector >
// You can use "dbg(..)" in expressions:
int32_t factorial ( int32_t n) {
if ( dbg (n <= 1 )) {
return dbg ( 1 );
} else {
return dbg (n * factorial (n - 1 ));
}
}
int32_t main () {
std::string message = " hello " ;
dbg (message); // [example.cpp:15 (main)] message = "hello" (std::string)
const int32_t a = 2 ;
const int32_t b = dbg ( 3 * a) + 1 ; // [example.cpp:18 (main)] 3 * a = 6 (int32_t)
std::vector< int32_t > numbers{b, 13 , 42 };
dbg (numbers); // [example.cpp:21 (main)] numbers = {7, 13, 42} (std::vector<int32_t>)
dbg ( " this line is executed " ); // [example.cpp:23 (main)] this line is executed
factorial ( 4 );
return 0 ;
}โค้ดด้านบนสร้างผลลัพธ์นี้ (ลองด้วยตัวเอง):
std::optional ฯลฯdbg.h ออกคำเตือนคอมไพเลอร์เมื่อรวมไว้ (ดังนั้นคุณอย่าลืมลบออก) เพื่อให้สิ่งนี้ใช้งานได้จริง ส่วนหัว dbg.h ควรพร้อมใช้งานจากสถานที่ที่แตกต่างกันทุกประเภทและในสภาพแวดล้อมทุกประเภท วิธีที่รวดเร็วและสกปรกคือการคัดลอกไฟล์ส่วนหัวไปที่ /usr/local/include หรือโคลนที่เก็บและ symlink dbg.h ไปที่ /usr/local/include/dbg.h
git clone https://github.com/sharkdp/dbg-macro
sudo ln -s $( readlink -f dbg-macro/dbg.h ) /usr/local/include/dbg.hหากคุณไม่ต้องการทำการเปลี่ยนแปลงระบบไฟล์ของคุณโดยไม่ได้ติดตาม ให้ตรวจสอบด้านล่างว่ามีแพ็คเกจสำหรับระบบปฏิบัติการหรือตัวจัดการแพ็คเกจของคุณหรือไม่
คุณสามารถติดตั้ง dbg-macro จาก AUR:
yay -S dbg-macro คุณสามารถติดตั้งพอร์ต dbg-macro ผ่านทาง:
vcpkg install dbg-macro CMakeLists.txt
cmake_minimum_required ( VERSION 3.11) # FetchContent added in cmake 3.11
project (app) # name of executable
set (CMAKE_CXX_STANDARD 17)
# dbg-macro
include (FetchContent)
FetchContent_Declare(dbg_macro GIT_REPOSITORY https://github.com/sharkdp/dbg-macro)
FetchContent_MakeAvailable(dbg_macro)
add_executable ( ${PROJECT_NAME} main.cpp) # your source files goes here
target_link_libraries ( ${PROJECT_NAME} PRIVATE dbg_macro) # make dbg.h available main.cpp
# include < dbg.h >
int main () {
dbg ( 42 , " hello world " , false );
return 0 ;
}DBG_MACRO_DISABLE เพื่อปิดใช้งานแมโคร dbg(…) (เช่น ทำให้เป็นแบบ no-op)DBG_MACRO_NO_WARNING เพื่อปิดใช้งานคำเตือน "ส่วนหัว 'dbg.h' จะรวมอยู่ในฐานโค้ดของคุณ"DBG_MACRO_FORCE_COLOR เพื่อบังคับให้เอาต์พุตเป็นสีและข้ามการตรวจสอบ tty คุณสามารถส่งผ่านอาร์กิวเมนต์หลายรายการไปยังแมโคร dbg(…) ผลลัพธ์ของ dbg(x, y, z) เหมือนกับ dbg(x); dbg(y); dbg(z); -
dbg ( 42 , " hello world " , false );โปรดทราบว่าคุณต้องใส่ "เครื่องหมายจุลภาคที่ไม่มีการป้องกัน" ในวงเล็บ:
dbg ( " a vector: " , (std::vector< int >{ 2 , 3 , 4 })); หากคุณต้องการจัดรูปแบบจำนวนเต็มในรูปแบบเลขฐานสิบหก ฐานแปด หรือไบนารี คุณสามารถล้อมมันไว้ใน dbg::hex(…) , dbg::oct(…) หรือ dbg::bin(…) :
const uint32_t secret = 12648430 ;
dbg (dbg::hex(secret)); dbg(…) พิมพ์ประเภทของแต่ละค่าในวงเล็บแล้ว (ดูภาพหน้าจอด้านบน) แต่บางครั้งคุณเพียงต้องการพิมพ์ประเภท (อาจเป็นเพราะคุณไม่มีค่าสำหรับประเภทนั้น) ในกรณีนี้ คุณสามารถใช้ตัวช่วย dbg::type<T>() เพื่อพิมพ์ประเภทที่กำหนด T ได้ ตัวอย่างเช่น:
template < typename T>
void my_function_template () {
using MyDependentType = typename std::remove_reference<T>::type&&;
dbg (dbg::type<MyDependentType>());
} หากต้องการพิมพ์การประทับเวลา คุณสามารถใช้ตัวช่วย dbg::time() ได้:
dbg (dbg::time()); หากคุณต้องการให้ dbg(…) ทำงานให้กับประเภทข้อมูลที่คุณกำหนดเอง คุณสามารถโอเวอร์โหลดโอเปอ operator<< สำหรับ std::ostream& :
std::ostream& operator <<(std::ostream& out, const user_defined_type& v) {
out << " … " ;
return out;
} หากคุณต้องการแก้ไขชื่อประเภทที่พิมพ์โดย dbg(…) คุณสามารถเพิ่ม get_type_name โอเวอร์โหลดแบบกำหนดเองได้:
// Customization point for type information
namespace dbg {
std::string get_type_name (type_tag< bool >) {
return " truth value " ;
}
} หากคุณต้องการสนับสนุน dbg-macro ต่อไปนี้คือวิธีที่คุณสามารถสร้างการทดสอบและการสาธิต:
ตรวจสอบให้แน่ใจว่าโมดูลย่อยเป็นปัจจุบัน:
git submodule update --init จากนั้น ใช้เวิร์กโฟลว์ cmake ทั่วไป การใช้ -DCMAKE_CXX_STANDARD=17 เป็นทางเลือก แต่แนะนำเพื่อให้ชุดคุณลักษณะที่ใหญ่ที่สุดเปิดใช้งาน:
mkdir build
cd build
cmake .. -DCMAKE_CXX_STANDARD=17
makeหากต้องการดำเนินการทดสอบ เพียงโทร:
make test คุณสามารถค้นหาหน่วยการทดสอบได้ใน tests/basic.cpp
โปรเจ็กต์นี้ได้รับแรงบันดาลใจจากแมโคร Rusts dbg!(…)