Shell脚本中传递CMAKE_CXX_FLAGS的CMake多编译参数问题
Let's break down what's going wrong with your current approach and walk through the right ways to handle this parameter passing.
The Problem With Your Original Script
Your current array assignment uses escaped spaces, but when you pass ${cmake_params[$i]} to CMake, it doesn't behave as expected. Here's why:
When you write:
cmake_params[1]=-DCMAKE_CXX_FLAGS=-O2\ -DNDEBUG
Bash stores the value as -DCMAKE_CXX_FLAGS=-O2 -DNDEBUG. When you wrap this in quotes and pass it to CMake, CMake parses this as two separate things:
- Set
CMAKE_CXX_FLAGSto-O2 - Treat
-DNDEBUGas a standalone-Dparameter (which enables theNDEBUGvariable without it being part of your compiler flags)
This isn't what you want—you need -O2 and -DNDEBUG to both be part of the CMAKE_CXX_FLAGS value.
Solution 1: Wrap the Flag Value in Quotes
Store each CMake parameter with quotes around the CMAKE_CXX_FLAGS value, so CMake recognizes the entire string as the flag set:
# Define your configurations with quoted flag values cmake_params[1]="-DCMAKE_CXX_FLAGS='-O2 -DNDEBUG'" cmake_params[2]="-DCMAKE_CXX_FLAGS='-march=native -O2 -DNDEBUG'" # Compilation loop for i in {1..2} do # Clean up old build and create new one rm -rf build && mkdir build && cd build # Pass the parameter correctly cmake "${cmake_params[$i]}" .. make cd .. done
The inner single quotes ensure CMake treats -O2 -DNDEBUG as a single value for CMAKE_CXX_FLAGS.
Solution 2: Separate Flag Values for Clarity (Recommended)
A cleaner approach is to store just the compiler flag strings, then construct the CMake parameter dynamically. This makes your script easier to read and modify:
# Define just the compiler flag sets cxx_flag_sets=( "-O2 -DNDEBUG" "-march=native -O2 -DNDEBUG" ) # Loop through each flag set for flags in "${cxx_flag_sets[@]}" do # Create a unique build directory for each configuration (avoids cache issues) build_dir="build-$(echo "$flags" | tr ' ' '-')" rm -rf "$build_dir" && mkdir "$build_dir" && cd "$build_dir" # Pass the flags directly to CMake cmake -DCMAKE_CXX_FLAGS="$flags" .. make cd .. done
This way, Bash handles the quoting automatically, ensuring CMake receives -DCMAKE_CXX_FLAGS="-O2 -DNDEBUG" as a single, correctly parsed parameter.
Bonus: Keep Multiple Builds
If you want to retain all compiled versions instead of overwriting them every time, use unique build directories (like in Solution 2). This lets you compare outputs or reuse builds later without recompiling from scratch.
内容的提问来源于stack exchange,提问作者Max Beikirch

