constexpr int MAX_SIZE = 100; static_assert(MAX_SIZE > 10, "Buffer too small"); // 編譯失敗若條件為假 static_assert(sizeof(void*) == 8, "64-bit required");
優於 #error:可依賴模板參數、constexpr 函數結果,錯誤信息可定制。
int x = 0;
decltype(x) y = 10; // int
decltype((x)) z = y; // int& (加括號 → 引用類型)
decltype(x + y) w = 0; // int (表達式非左值)
// 尾置返回類型配合 decltype
template <typename T, typename U>
auto add(T a, U b) -> decltype(a + b) { return a + b; }
規則:decltype(var) 保留 cv/引用;decltype(expr) 表達式為左值則得 T&,右值得 T。
auto i = 42; // int auto d = 3.14; // double auto p = new auto(10); // int* (C++11 支持 new auto) auto& ref = i; // int& const auto& cref = i; // const int& // 範圍 for 配合 auto for (auto& x : vec) x *= 2; for (const auto& x : vec) cout << x; // 僅讀用 const&
VS2010 限制:不支持 new auto(expr) 動態分配語法,會報錯誤。
// 基本語法:[捕獲列表](參數)->返回類型 { 函數體 }
auto add = [](int a, int b) { return a + b; }; // 返回類型自動推導
auto greet = [](const string& name) -> string { return "Hello " + name; };
// 捕獲列表
int factor = 10;
auto scale = [factor](int x) { return x * factor; }; // 值捕獲
auto scaleRef = [&factor](int x) { return x * factor; } // 引用捕獲
auto allVal = [=](int x) { return x * factor; } // 全部值捕獲
auto allRef = [&](int x) { return x * factor; } // 全部引用捕獲
// STL 算法中使用
vector v = {3,1,4,1,5};
sort(v.begin(), v.end(), [](int a, int b){ return a > b; }); // 降序
int cnt = count_if(v.begin(), v.end(), [](int x){ return x % 2 == 0; });
std::move(x) 轉換結果。class String {
char* data; size_t len;
public:
String(const char* s) : len(strlen(s)) { data = new char[len+1]; strcpy(data, s); }
// 移動構造:竊取資源,置空源對象
String(String&& other) noexcept : data(other.data), len(other.len) {
other.data = nullptr; other.len = 0;
}
// 移動賦值
String& operator=(String&& other) noexcept {
if (this != &other) {
delete[] data;
data = other.data; len = other.len;
other.data = nullptr; other.len = 0;
}
return *this;
}
~String() { delete[] data; }
};
String s1("hello");
String s2 = std::move(s1); // 調用移動構造,s1 置空
// 完美轉發:保持實參左/右值屬性
template <typename T>
void wrapper(T&& arg) {
foo(std::forward<T>(arg)); // 左值傳左值,右值傳右值
}
VS2010 實現細節:std::move 利用 _Remove_reference traits 去除引用再加 &&;std::forward 利用 identity 保持類型不變。
noexcept,否則 STL 容器擴容時會退回拷貝。this 時注意對象生命週期,避免懸空指針。auto 推導 initializer_list 時需顯式指定:auto x = {1,2}; // std::initializer_list。