From 326e8fa7538c69757822dac3fbd797f295b9af58 Mon Sep 17 00:00:00 2001 From: YdrMaster Date: Fri, 6 Dec 2024 15:09:58 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=89=A9=E5=85=85=E5=88=B0=2034=20?= =?UTF-8?q?=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: YdrMaster --- exercises/06_array/main.cpp | 26 ++++ exercises/{06_loop => 07_loop}/main.cpp | 0 exercises/08_pointer/main.cpp | 28 +++++ .../{07_enum&union => 09_enum&union}/main.cpp | 0 exercises/{08_trivial => 10_trivial}/main.cpp | 0 exercises/{09_method => 11_method}/main.cpp | 0 .../main.cpp | 0 exercises/{11_class => 13_class}/main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../{14_class_move => 16_class_move}/main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../main.cpp | 0 .../{22_std_array => 24_std_array}/main.cpp | 0 .../{23_std_vector => 25_std_vector}/main.cpp | 0 .../main.cpp | 0 exercises/{25_strides => 27_strides}/main.cpp | 0 .../{26_std_string => 28_std_string}/main.cpp | 0 exercises/{27_std_map => 29_std_map}/main.cpp | 0 exercises/30_std_unique_ptr/main.cpp | 74 ++++++++++++ exercises/31_std_shared_ptr/main.cpp | 45 +++++++ .../main.cpp | 0 .../main.cpp | 0 exercises/xmake.lua | 112 ++++++++++-------- learn/summary.cpp | 14 ++- 30 files changed, 245 insertions(+), 54 deletions(-) create mode 100644 exercises/06_array/main.cpp rename exercises/{06_loop => 07_loop}/main.cpp (100%) create mode 100644 exercises/08_pointer/main.cpp rename exercises/{07_enum&union => 09_enum&union}/main.cpp (100%) rename exercises/{08_trivial => 10_trivial}/main.cpp (100%) rename exercises/{09_method => 11_method}/main.cpp (100%) rename exercises/{10_method_const => 12_method_const}/main.cpp (100%) rename exercises/{11_class => 13_class}/main.cpp (100%) rename exercises/{12_class_destruct => 14_class_destruct}/main.cpp (100%) rename exercises/{13_class_clone => 15_class_clone}/main.cpp (100%) rename exercises/{14_class_move => 16_class_move}/main.cpp (100%) rename exercises/{15_class_derive => 17_class_derive}/main.cpp (100%) rename exercises/{16_class_virtual => 18_class_virtual}/main.cpp (100%) rename exercises/{17_class_virtual_destruct => 19_class_virtual_destruct}/main.cpp (100%) rename exercises/{18_function_template => 20_function_template}/main.cpp (100%) rename exercises/{19_runtime_datatype => 21_runtime_datatype}/main.cpp (100%) rename exercises/{20_class_template => 22_class_template}/main.cpp (100%) rename exercises/{21_template_const => 23_template_const}/main.cpp (100%) rename exercises/{22_std_array => 24_std_array}/main.cpp (100%) rename exercises/{23_std_vector => 25_std_vector}/main.cpp (100%) rename exercises/{24_std_vector_bool => 26_std_vector_bool}/main.cpp (100%) rename exercises/{25_strides => 27_strides}/main.cpp (100%) rename exercises/{26_std_string => 28_std_string}/main.cpp (100%) rename exercises/{27_std_map => 29_std_map}/main.cpp (100%) create mode 100644 exercises/30_std_unique_ptr/main.cpp create mode 100644 exercises/31_std_shared_ptr/main.cpp rename exercises/{28_std_transform => 32_std_transform}/main.cpp (100%) rename exercises/{29_std_accumulate => 33_std_accumulate}/main.cpp (100%) diff --git a/exercises/06_array/main.cpp b/exercises/06_array/main.cpp new file mode 100644 index 00000000..61ed99ec --- /dev/null +++ b/exercises/06_array/main.cpp @@ -0,0 +1,26 @@ +#include "../exercise.h" + +// READ: 数组 + +unsigned long long arr[90]{0, 1}; +unsigned long long fibonacci(int i) { + switch (i) { + case 0: + return 0; + case 1: + return 1; + default: + // TODO: 补全三目表达式缺失的部分 + return ? : (arr[i] = fibonacci(i - 1) + fibonacci(i - 2)); + } +} + +int main(int argc, char **argv) { + // TODO: 为此 ASSERT 填写正确的值 + ASSERT(sizeof(arr) == ?, "sizeof array is size of all its elements"); + // ---- 不要修改以下代码 ---- + ASSERT(fibonacci(2) == 1, "fibonacci(2) should be 1"); + ASSERT(fibonacci(20) == 6765, "fibonacci(20) should be 6765"); + ASSERT(fibonacci(80) == 23416728348467685, "fibonacci(80) should be 23416728348467685"); + return 0; +} diff --git a/exercises/06_loop/main.cpp b/exercises/07_loop/main.cpp similarity index 100% rename from exercises/06_loop/main.cpp rename to exercises/07_loop/main.cpp diff --git a/exercises/08_pointer/main.cpp b/exercises/08_pointer/main.cpp new file mode 100644 index 00000000..ba37173f --- /dev/null +++ b/exercises/08_pointer/main.cpp @@ -0,0 +1,28 @@ +#include "../exercise.h" + +// READ: 数组向指针退化 +bool is_fibonacci(int *ptr, int len, int stride) { + ASSERT(len >= 3, "`len` should be at least 3"); + // TODO: 编写代码判断从 ptr 开始,每 stride 个元素取 1 个元素,组成长度为 n 的数列是否满足 + // arr[i + 2] = arr[i] + arr[i + 1] + return true; +} + +// ---- 不要修改以下代码 ---- +int main(int argc, char **argv) { + int arr0[]{0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55}, + arr1[]{0, 1, 2, 3, 4, 5, 6}, + arr2[]{99, 98, 4, 1, 7, 2, 11, 3, 18, 5, 29, 8, 47, 13, 76, 21, 123, 34, 199, 55, 322, 0, 0}; + // clang-format off + ASSERT( is_fibonacci(arr0 , sizeof(arr0) / sizeof(*arr0) , 1), "arr0 is Fibonacci" ); + ASSERT( is_fibonacci(arr0 + 2, sizeof(arr0) / sizeof(*arr0) - 4, 1), "part of arr0 is Fibonacci" ); + ASSERT(!is_fibonacci(arr1 , sizeof(arr1) / sizeof(*arr1) , 1), "arr1 is not Fibonacci"); + ASSERT( is_fibonacci(arr1 + 1, 3 , 1), "part of arr1 is Fibonacci" ); + ASSERT(!is_fibonacci(arr2 , sizeof(arr2) / sizeof(*arr2) , 1), "arr2 is not Fibonacci"); + ASSERT( is_fibonacci(arr2 + 2, 10 , 2), "part of arr2 is Fibonacci" ); + ASSERT( is_fibonacci(arr2 + 3, 9 , 2), "part of arr2 is Fibonacci" ); + ASSERT(!is_fibonacci(arr2 + 3, 10 , 2), "guard check" ); + ASSERT(!is_fibonacci(arr2 + 1, 10 , 2), "guard check" ); + // clang-format on + return 0; +} diff --git a/exercises/07_enum&union/main.cpp b/exercises/09_enum&union/main.cpp similarity index 100% rename from exercises/07_enum&union/main.cpp rename to exercises/09_enum&union/main.cpp diff --git a/exercises/08_trivial/main.cpp b/exercises/10_trivial/main.cpp similarity index 100% rename from exercises/08_trivial/main.cpp rename to exercises/10_trivial/main.cpp diff --git a/exercises/09_method/main.cpp b/exercises/11_method/main.cpp similarity index 100% rename from exercises/09_method/main.cpp rename to exercises/11_method/main.cpp diff --git a/exercises/10_method_const/main.cpp b/exercises/12_method_const/main.cpp similarity index 100% rename from exercises/10_method_const/main.cpp rename to exercises/12_method_const/main.cpp diff --git a/exercises/11_class/main.cpp b/exercises/13_class/main.cpp similarity index 100% rename from exercises/11_class/main.cpp rename to exercises/13_class/main.cpp diff --git a/exercises/12_class_destruct/main.cpp b/exercises/14_class_destruct/main.cpp similarity index 100% rename from exercises/12_class_destruct/main.cpp rename to exercises/14_class_destruct/main.cpp diff --git a/exercises/13_class_clone/main.cpp b/exercises/15_class_clone/main.cpp similarity index 100% rename from exercises/13_class_clone/main.cpp rename to exercises/15_class_clone/main.cpp diff --git a/exercises/14_class_move/main.cpp b/exercises/16_class_move/main.cpp similarity index 100% rename from exercises/14_class_move/main.cpp rename to exercises/16_class_move/main.cpp diff --git a/exercises/15_class_derive/main.cpp b/exercises/17_class_derive/main.cpp similarity index 100% rename from exercises/15_class_derive/main.cpp rename to exercises/17_class_derive/main.cpp diff --git a/exercises/16_class_virtual/main.cpp b/exercises/18_class_virtual/main.cpp similarity index 100% rename from exercises/16_class_virtual/main.cpp rename to exercises/18_class_virtual/main.cpp diff --git a/exercises/17_class_virtual_destruct/main.cpp b/exercises/19_class_virtual_destruct/main.cpp similarity index 100% rename from exercises/17_class_virtual_destruct/main.cpp rename to exercises/19_class_virtual_destruct/main.cpp diff --git a/exercises/18_function_template/main.cpp b/exercises/20_function_template/main.cpp similarity index 100% rename from exercises/18_function_template/main.cpp rename to exercises/20_function_template/main.cpp diff --git a/exercises/19_runtime_datatype/main.cpp b/exercises/21_runtime_datatype/main.cpp similarity index 100% rename from exercises/19_runtime_datatype/main.cpp rename to exercises/21_runtime_datatype/main.cpp diff --git a/exercises/20_class_template/main.cpp b/exercises/22_class_template/main.cpp similarity index 100% rename from exercises/20_class_template/main.cpp rename to exercises/22_class_template/main.cpp diff --git a/exercises/21_template_const/main.cpp b/exercises/23_template_const/main.cpp similarity index 100% rename from exercises/21_template_const/main.cpp rename to exercises/23_template_const/main.cpp diff --git a/exercises/22_std_array/main.cpp b/exercises/24_std_array/main.cpp similarity index 100% rename from exercises/22_std_array/main.cpp rename to exercises/24_std_array/main.cpp diff --git a/exercises/23_std_vector/main.cpp b/exercises/25_std_vector/main.cpp similarity index 100% rename from exercises/23_std_vector/main.cpp rename to exercises/25_std_vector/main.cpp diff --git a/exercises/24_std_vector_bool/main.cpp b/exercises/26_std_vector_bool/main.cpp similarity index 100% rename from exercises/24_std_vector_bool/main.cpp rename to exercises/26_std_vector_bool/main.cpp diff --git a/exercises/25_strides/main.cpp b/exercises/27_strides/main.cpp similarity index 100% rename from exercises/25_strides/main.cpp rename to exercises/27_strides/main.cpp diff --git a/exercises/26_std_string/main.cpp b/exercises/28_std_string/main.cpp similarity index 100% rename from exercises/26_std_string/main.cpp rename to exercises/28_std_string/main.cpp diff --git a/exercises/27_std_map/main.cpp b/exercises/29_std_map/main.cpp similarity index 100% rename from exercises/27_std_map/main.cpp rename to exercises/29_std_map/main.cpp diff --git a/exercises/30_std_unique_ptr/main.cpp b/exercises/30_std_unique_ptr/main.cpp new file mode 100644 index 00000000..ab75c801 --- /dev/null +++ b/exercises/30_std_unique_ptr/main.cpp @@ -0,0 +1,74 @@ +#include "../exercise.h" +#include +#include +#include + +// READ: `std::unique_ptr` + +std::vector RECORDS; + +class Resource { + std::string _records; + +public: + void record(char record) { + _records.push_back(record); + } + + ~Resource() { + RECORDS.push_back(_records); + } +}; + +using Unique = std::unique_ptr; +Unique reset(Unique ptr) { + if (ptr) { + ptr->record('r'); + } + return std::make_unique(); +} +Unique drop(Unique ptr) { + if (ptr) { + ptr->record('d'); + } + return nullptr; +} +Unique forward(Unique ptr) { + if (ptr) { + ptr->record('f'); + } + return ptr; +} + +int main(int argc, char **argv) { + std::vector problems[3]; + + drop(forward(reset(nullptr))); + problems[0] = std::move(RECORDS); + + forward(drop(reset(forward(forward(reset(nullptr)))))); + problems[1] = std::move(RECORDS); + + drop(drop(reset(drop(reset(reset(nullptr)))))); + problems[2] = std::move(RECORDS); + + // ---- 不要修改以上代码 ---- + + std::vector answers[]{ + {"fd"}, + // TODO: 分析 problems[1] 中资源的生命周期,将记录填入 `std::vector` + {"", "", "", "", "", "", "", ""}, + {"", "", "", "", "", "", "", ""}, + }; + + // ---- 不要修改以下代码 ---- + + for (auto i = 0; i < 3; ++i) { + ASSERT(problems[i].size() == answers[i].size(), "wrong size"); + for (auto j = 0; j < problems[i].size(); ++j) { + ASSERT(std::strcmp(problems[i][j].c_str(), answers[i][j]) == 0, "wrong location"); + } + } + + return 0; +} diff --git a/exercises/31_std_shared_ptr/main.cpp b/exercises/31_std_shared_ptr/main.cpp new file mode 100644 index 00000000..febbbcc6 --- /dev/null +++ b/exercises/31_std_shared_ptr/main.cpp @@ -0,0 +1,45 @@ +#include "../exercise.h" +#include + +// READ: `std::shared_ptr` +// READ: `std::weak_ptr` + +// TODO: 将下列 `?` 替换为正确的值 +int main(int argc, char **argv) { + auto shared = std::make_shared(10); + std::shared_ptr ptrs[]{shared, shared, shared}; + + std::weak_ptr observer = shared; + ASSERT(observer.use_count() == ?, ""); + + ptrs[0].reset(); + ASSERT(observer.use_count() == ?, ""); + + ptrs[1] = nullptr; + ASSERT(observer.use_count() == ?, ""); + + ptrs[2] = std::make_shared(*shared); + ASSERT(observer.use_count() == ?, ""); + + ptrs[0] = shared; + ptrs[1] = shared; + ptrs[2] = std::move(shared); + ASSERT(observer.use_count() == ?, ""); + + std::ignore = std::move(ptrs[0]); + ptrs[1] = std::move(ptrs[1]); + ptrs[1] = std::move(ptrs[2]); + ASSERT(observer.use_count() == ?, ""); + + shared = observer.lock(); + ASSERT(observer.use_count() == ?, ""); + + shared = nullptr; + for (auto &ptr : ptrs) ptr = nullptr; + ASSERT(observer.use_count() == ?, ""); + + shared = observer.lock(); + ASSERT(observer.use_count() == ?, ""); + + return 0; +} diff --git a/exercises/28_std_transform/main.cpp b/exercises/32_std_transform/main.cpp similarity index 100% rename from exercises/28_std_transform/main.cpp rename to exercises/32_std_transform/main.cpp diff --git a/exercises/29_std_accumulate/main.cpp b/exercises/33_std_accumulate/main.cpp similarity index 100% rename from exercises/29_std_accumulate/main.cpp rename to exercises/33_std_accumulate/main.cpp diff --git a/exercises/xmake.lua b/exercises/xmake.lua index f7c656f2..0c3b11bf 100644 --- a/exercises/xmake.lua +++ b/exercises/xmake.lua @@ -28,100 +28,116 @@ target("exercise04") target("exercise05") add_files("05_constexpr/main.cpp") --- 循环 +-- 数组 target("exercise06") - add_files("06_loop/main.cpp") + add_files("06_array/main.cpp") --- 枚举/联合体 +-- 循环 target("exercise07") - add_files("07_enum&union/main.cpp") + add_files("07_loop/main.cpp") --- “普通”类型 +-- 指针 target("exercise08") - add_files("08_trivial/main.cpp") + add_files("08_pointer/main.cpp") --- 方法 +-- 枚举/联合体 target("exercise09") - add_files("09_method/main.cpp") + add_files("09_enum&union/main.cpp") --- const 修饰方法 +-- “普通”类型 target("exercise10") - add_files("10_method_const/main.cpp") + add_files("10_trivial/main.cpp") --- 类 +-- 方法 target("exercise11") - add_files("11_class/main.cpp") + add_files("11_method/main.cpp") --- 析构器 +-- const 修饰方法 target("exercise12") - add_files("12_class_destruct/main.cpp") + add_files("12_method_const/main.cpp") --- 复制构造函数 +-- 类 target("exercise13") - add_files("13_class_clone/main.cpp") + add_files("13_class/main.cpp") --- 移动语义 +-- 析构器 target("exercise14") - add_files("14_class_move/main.cpp") + add_files("14_class_destruct/main.cpp") --- 派生 +-- 复制构造函数 target("exercise15") - add_files("15_class_derive/main.cpp") + add_files("15_class_clone/main.cpp") --- 虚函数 +-- 移动语义 target("exercise16") - add_files("16_class_virtual/main.cpp") + add_files("16_class_move/main.cpp") --- 虚析构函数 +-- 派生 target("exercise17") - add_files("17_class_virtual_destruct/main.cpp") + add_files("17_class_derive/main.cpp") --- 函数模板 +-- 虚函数 target("exercise18") - add_files("18_function_template/main.cpp") + add_files("18_class_virtual/main.cpp") --- 习题:用于编译器的运行时类型 +-- 虚析构函数 target("exercise19") - add_files("19_runtime_datatype/main.cpp") + add_files("19_class_virtual_destruct/main.cpp") --- 类模板 +-- 函数模板 target("exercise20") - add_files("20_class_template/main.cpp") + add_files("20_function_template/main.cpp") --- 模板非类型实参 +-- 习题:用于编译器的运行时类型 target("exercise21") - add_files("21_template_const/main.cpp") + add_files("21_runtime_datatype/main.cpp") --- std::array +-- 类模板 target("exercise22") - add_files("22_std_array/main.cpp") + add_files("22_class_template/main.cpp") --- std::vector +-- 模板非类型实参 target("exercise23") - add_files("23_std_vector/main.cpp") + add_files("23_template_const/main.cpp") --- std::vector +-- std::array target("exercise24") - add_files("24_std_vector_bool/main.cpp") + add_files("24_std_array/main.cpp") --- 习题:步长计算 +-- std::vector target("exercise25") - add_files("25_strides/main.cpp") + add_files("25_std_vector/main.cpp") --- std::string +-- std::vector target("exercise26") - add_files("26_std_string/main.cpp") + add_files("26_std_vector_bool/main.cpp") --- std::map +-- 习题:步长计算 target("exercise27") - add_files("27_std_map/main.cpp") + add_files("27_strides/main.cpp") --- std::transform +-- std::string target("exercise28") - add_files("28_std_transform/main.cpp") + add_files("28_std_string/main.cpp") --- std::accumulate +-- std::map target("exercise29") - add_files("29_std_accumulate/main.cpp") + add_files("29_std_map/main.cpp") + +-- std::transform +target("exercise30") + add_files("30_std_unique_ptr/main.cpp") + +-- std::accumulate +target("exercise31") + add_files("31_std_shared_ptr/main.cpp") + +-- std::transform +target("exercise32") + add_files("32_std_transform/main.cpp") + +-- std::accumulate +target("exercise33") + add_files("33_std_accumulate/main.cpp") -- TODO: lambda; deque; forward_list; fs; thread; mutex; diff --git a/learn/summary.cpp b/learn/summary.cpp index 775bd4ae..7c4ca371 100644 --- a/learn/summary.cpp +++ b/learn/summary.cpp @@ -9,7 +9,7 @@ #include #include -constexpr auto MAX_EXERCISE = 29; +constexpr auto MAX_EXERCISE = 33; int main(int argc, char **argv) { if (argc == 1) { @@ -34,13 +34,15 @@ int main(int argc, char **argv) { std::vector threads; threads.reserve(concurrency); + std::cout << "concurrency: " << concurrency << std::endl; Log log{Null{}}; for (auto i = 0u; i <= concurrency; ++i) { - threads.emplace_back([&log, &k] { - int i = k.fetch_add(1); - while (i <= MAX_EXERCISE) { - log << i; - i = k.fetch_add(1); + threads.emplace_back([i, &log, &k] { + int j = k.fetch_add(1); + while (j <= MAX_EXERCISE) { + std::printf("run %d at %d\n", j, i); + log << j; + j = k.fetch_add(1); } }); }