From 7d274532a8dbca4125ba6e0fe3f8111228e0ee22 Mon Sep 17 00:00:00 2001 From: JimmyBynex Date: Sat, 10 Jan 2026 22:57:24 +0800 Subject: [PATCH] finished finished --- exercises/00_hello_world/main.cpp | 2 +- exercises/00_hello_world/main.exe | Bin 0 -> 76554 bytes exercises/01_variable&add/main.cpp | 1 + exercises/02_function/main.cpp | 2 + exercises/03_argument¶meter/main.cpp | 8 +-- exercises/04_static/main.cpp | 10 +-- exercises/05_constexpr/main.cpp | 2 +- exercises/06_array/main.cpp | 4 +- exercises/07_loop/main.cpp | 4 +- exercises/08_pointer/main.cpp | 5 ++ exercises/09_enum&union/main.cpp | 3 +- exercises/10_trivial/main.cpp | 7 +- exercises/11_method/main.cpp | 5 +- exercises/12_method_const/main.cpp | 3 +- exercises/13_class/main.cpp | 5 +- exercises/14_class_destruct/main.cpp | 11 +++- exercises/15_class_clone/main.cpp | 24 +++++-- exercises/16_class_move/main.cpp | 27 ++++++-- exercises/17_class_derive/main.cpp | 6 +- exercises/18_class_virtual/main.cpp | 40 +++++------ exercises/19_class_virtual_destruct/main.cpp | 29 ++++---- exercises/20_function_template/main.cpp | 5 +- exercises/21_runtime_datatype/main.cpp | 8 ++- exercises/22_class_template/main.cpp | 35 ++++++++++ exercises/23_template_const/main.cpp | 9 +++ exercises/24_std_array/main.cpp | 16 ++--- exercises/25_std_vector/main.cpp | 66 +++++++++---------- exercises/26_std_vector_bool/main.cpp | 16 ++--- exercises/27_strides/main.cpp | 5 ++ exercises/28_std_string/main.cpp | 6 +- exercises/29_std_map/main.cpp | 2 + exercises/30_std_unique_ptr/main.cpp | 6 +- exercises/31_std_shared_ptr/main.cpp | 18 ++--- exercises/32_std_transform/main.cpp | 3 + exercises/33_std_accumulate/main.cpp | 2 +- 35 files changed, 255 insertions(+), 140 deletions(-) create mode 100644 exercises/00_hello_world/main.exe diff --git a/exercises/00_hello_world/main.cpp b/exercises/00_hello_world/main.cpp index 8866f3c15..4b96772dc 100644 --- a/exercises/00_hello_world/main.cpp +++ b/exercises/00_hello_world/main.cpp @@ -6,6 +6,6 @@ int main(int argc, char **argv) { // TODO: 在控制台输出 "Hello, InfiniTensor!" 并换行 - std::cout : "Hello, InfiniTensor!" + std::endl; + std::cout << "Hello, InfiniTensor!\n" << std::endl; return 0; } diff --git a/exercises/00_hello_world/main.exe b/exercises/00_hello_world/main.exe new file mode 100644 index 0000000000000000000000000000000000000000..8cd8d3d3d0f86eb9823007ed13fb395e9520af22 GIT binary patch literal 76554 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 static unsigned long long fibonacci(int i) { // TODO: 为缓存设置正确的初始值 - static unsigned long long cache[96], cached; + static unsigned long long cache[96]={0, 1}, cached=2; // TODO: 设置正确的循环条件 - for (; false; ++cached) { + for (; cached <= i; ++cached) { cache[cached] = cache[cached - 1] + cache[cached - 2]; } return cache[i]; diff --git a/exercises/08_pointer/main.cpp b/exercises/08_pointer/main.cpp index ba37173f5..325661e29 100644 --- a/exercises/08_pointer/main.cpp +++ b/exercises/08_pointer/main.cpp @@ -5,6 +5,11 @@ 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] + for (int i = 0; i < len - 2; ++i) { + if (*(ptr + (i + 2) * stride) != *(ptr + i * stride) + *(ptr + (i + 1) * stride)) { + return false; + } + } return true; } diff --git a/exercises/09_enum&union/main.cpp b/exercises/09_enum&union/main.cpp index 3f2cec768..01edb6952 100644 --- a/exercises/09_enum&union/main.cpp +++ b/exercises/09_enum&union/main.cpp @@ -34,10 +34,9 @@ ColorEnum convert_by_pun(Color c) { ColorEnum e; Color c; }; - TypePun pun; // TODO: 补全类型双关转换 - + pun.c = c; return pun.e; } diff --git a/exercises/10_trivial/main.cpp b/exercises/10_trivial/main.cpp index 6ba23e48e..d38918a8d 100644 --- a/exercises/10_trivial/main.cpp +++ b/exercises/10_trivial/main.cpp @@ -9,8 +9,8 @@ struct FibonacciCache { // TODO: 实现正确的缓存优化斐波那契计算 static unsigned long long fibonacci(FibonacciCache &cache, int i) { - for (; false; ++cached) { - cache[cached] = cache[cached - 1] + cache[cached - 2]; + for (; cache.cached <= i; ++cache.cached) { + cache.cache[cache.cached] = cache.cache[cache.cached - 1] + cache.cache[cache.cached - 2]; } return cache.cache[i]; } @@ -20,6 +20,9 @@ int main(int argc, char **argv) { // NOTICE: C/C++ 中,读取未初始化的变量(包括结构体变量)是未定义行为 // READ: 初始化的各种写法 FibonacciCache fib; + fib.cache[0] = 0; + fib.cache[1] = 1; + fib.cached = 2; ASSERT(fibonacci(fib, 10) == 55, "fibonacci(10) should be 55"); std::cout << "fibonacci(10) = " << fibonacci(fib, 10) << std::endl; return 0; diff --git a/exercises/11_method/main.cpp b/exercises/11_method/main.cpp index 0e08e0a36..a5ae0738b 100644 --- a/exercises/11_method/main.cpp +++ b/exercises/11_method/main.cpp @@ -6,7 +6,7 @@ struct Fibonacci { // TODO: 实现正确的缓存优化斐波那契计算 unsigned long long get(int i) { - for (; false; ++cached) { + for (; cached <= i; ++cached) { cache[cached] = cache[cached - 1] + cache[cached - 2]; } return cache[i]; @@ -16,6 +16,9 @@ struct Fibonacci { int main(int argc, char **argv) { // TODO: 初始化缓存结构体,使计算正确 Fibonacci fib; + fib.cache[0] = 0; + fib.cache[1] = 1; + fib.cached = 2; ASSERT(fib.get(10) == 55, "fibonacci(10) should be 55"); std::cout << "fibonacci(10) = " << fib.get(10) << std::endl; return 0; diff --git a/exercises/12_method_const/main.cpp b/exercises/12_method_const/main.cpp index 5521be4da..d1f7c64aa 100644 --- a/exercises/12_method_const/main.cpp +++ b/exercises/12_method_const/main.cpp @@ -5,7 +5,8 @@ struct Fibonacci { int numbers[11]; // TODO: 修改方法签名和实现,使测试通过 - int get(int i) { + int get(int i) const{ + return numbers[i]; } }; diff --git a/exercises/13_class/main.cpp b/exercises/13_class/main.cpp index 9afa98c5b..1590e2f27 100644 --- a/exercises/13_class/main.cpp +++ b/exercises/13_class/main.cpp @@ -15,10 +15,13 @@ class Fibonacci { public: // TODO: 实现构造器 // Fibonacci() + Fibonacci(): cache{0, 1}, cached(2) {} + // TODO: 实现正确的缓存优化斐波那契计算 size_t get(int i) { - for (; false; ++cached) { + + for (; cached <= i; ++cached) { cache[cached] = cache[cached - 1] + cache[cached - 2]; } return cache[i]; diff --git a/exercises/14_class_destruct/main.cpp b/exercises/14_class_destruct/main.cpp index 42150e8ca..e6dd85b59 100644 --- a/exercises/14_class_destruct/main.cpp +++ b/exercises/14_class_destruct/main.cpp @@ -11,14 +11,19 @@ class DynFibonacci { public: // TODO: 实现动态设置容量的构造器 - DynFibonacci(int capacity): cache(new ?), cached(?) {} + DynFibonacci(int capacity): cache(new size_t[capacity]), cached(2) { + cache[0] = 0; + cache[1] = 1; + } // TODO: 实现析构器,释放缓存空间 - ~DynFibonacci(); + ~DynFibonacci() { + delete[] cache; + } // TODO: 实现正确的缓存优化斐波那契计算 size_t get(int i) { - for (; false; ++cached) { + for (; cached <= i; ++cached) { cache[cached] = cache[cached - 1] + cache[cached - 2]; } return cache[i]; diff --git a/exercises/15_class_clone/main.cpp b/exercises/15_class_clone/main.cpp index f74b70391..fc91f8842 100644 --- a/exercises/15_class_clone/main.cpp +++ b/exercises/15_class_clone/main.cpp @@ -10,18 +10,30 @@ class DynFibonacci { public: // TODO: 实现动态设置容量的构造器 - DynFibonacci(int capacity): cache(new ?), cached(?) {} + DynFibonacci(int capacity): cache(new size_t[capacity+1]), cached(1) { + cache[0] = 0; + cache[1] = 1; + } // TODO: 实现复制构造器 - DynFibonacci(DynFibonacci const &) = delete; + DynFibonacci(DynFibonacci const &other): cache(nullptr), cached(other.cached) { + // 需要知道容量大小来分配数组,这里假设至少需要 cached + 1 的空间 + cache = new size_t[cached + 1]; + // 复制已缓存的数据 + for (int i = 0; i <= cached; ++i) { + cache[i] = other.cache[i]; + } + } // TODO: 实现析构器,释放缓存空间 - ~DynFibonacci(); - + ~DynFibonacci(){ + delete[] cache; + } + // TODO: 实现正确的缓存优化斐波那契计算 size_t get(int i) { - for (; false; ++cached) { - cache[cached] = cache[cached - 1] + cache[cached - 2]; + for (; cached < i; ++cached) { + cache[cached+1] = cache[cached] + cache[cached - 1]; } return cache[i]; } diff --git a/exercises/16_class_move/main.cpp b/exercises/16_class_move/main.cpp index 8d2c421da..9d2f105c2 100644 --- a/exercises/16_class_move/main.cpp +++ b/exercises/16_class_move/main.cpp @@ -15,21 +15,38 @@ class DynFibonacci { public: // TODO: 实现动态设置容量的构造器 - DynFibonacci(int capacity): cache(new ?), cached(?) {} + DynFibonacci(int capacity): cache(new size_t[capacity]), cached(2) { + cache[0] = 0; + cache[1] = 1; + } // TODO: 实现移动构造器 - DynFibonacci(DynFibonacci &&) noexcept = delete; + DynFibonacci(DynFibonacci &&other) noexcept: cache(other.cache), cached(other.cached) { + other.cache = nullptr; + other.cached = 0; + } // TODO: 实现移动赋值 // NOTICE: ⚠ 注意移动到自身问题 ⚠ - DynFibonacci &operator=(DynFibonacci &&) noexcept = delete; + DynFibonacci &operator=(DynFibonacci &&other) noexcept { + if (this != &other) { + delete[] cache; + cache = other.cache; + cached = other.cached; + other.cache = nullptr; + other.cached = 0; + } + return *this; + } // TODO: 实现析构器,释放缓存空间 - ~DynFibonacci(); + ~DynFibonacci() { + delete[] cache; + } // TODO: 实现正确的缓存优化斐波那契计算 size_t operator[](int i) { - for (; false; ++cached) { + for (; cached <= i; ++cached) { cache[cached] = cache[cached - 1] + cache[cached - 2]; } return cache[i]; diff --git a/exercises/17_class_derive/main.cpp b/exercises/17_class_derive/main.cpp index 819ae72fc..0c245df4f 100644 --- a/exercises/17_class_derive/main.cpp +++ b/exercises/17_class_derive/main.cpp @@ -50,9 +50,9 @@ int main(int argc, char **argv) { B b = B(3); // TODO: 补全三个类型的大小 - static_assert(sizeof(X) == ?, "There is an int in X"); - static_assert(sizeof(A) == ?, "There is an int in A"); - static_assert(sizeof(B) == ?, "B is an A with an X"); + static_assert(sizeof(X) == 4, "There is an int in X"); + static_assert(sizeof(A) == 4, "There is an int in A"); + static_assert(sizeof(B) == 8, "B is an A with an X"); i = 0; std::cout << std::endl diff --git a/exercises/18_class_virtual/main.cpp b/exercises/18_class_virtual/main.cpp index ac6382413..344709e4c 100644 --- a/exercises/18_class_virtual/main.cpp +++ b/exercises/18_class_virtual/main.cpp @@ -42,38 +42,38 @@ int main(int argc, char **argv) { C c; D d; - ASSERT(a.virtual_name() == '?', MSG); - ASSERT(b.virtual_name() == '?', MSG); - ASSERT(c.virtual_name() == '?', MSG); - ASSERT(d.virtual_name() == '?', MSG); - ASSERT(a.direct_name() == '?', MSG); - ASSERT(b.direct_name() == '?', MSG); - ASSERT(c.direct_name() == '?', MSG); - ASSERT(d.direct_name() == '?', MSG); + ASSERT(a.virtual_name() == 'A', MSG); + ASSERT(b.virtual_name() == 'B', MSG); + ASSERT(c.virtual_name() == 'C', MSG); + ASSERT(d.virtual_name() == 'C', MSG); + ASSERT(a.direct_name() == 'A', MSG); + ASSERT(b.direct_name() == 'B', MSG); + ASSERT(c.direct_name() == 'C', MSG); + ASSERT(d.direct_name() == 'D', MSG); A &rab = b; B &rbc = c; C &rcd = d; - ASSERT(rab.virtual_name() == '?', MSG); - ASSERT(rbc.virtual_name() == '?', MSG); - ASSERT(rcd.virtual_name() == '?', MSG); - ASSERT(rab.direct_name() == '?', MSG); - ASSERT(rbc.direct_name() == '?', MSG); - ASSERT(rcd.direct_name() == '?', MSG); + ASSERT(rab.virtual_name() == 'B', MSG); + ASSERT(rbc.virtual_name() == 'C', MSG); + ASSERT(rcd.virtual_name() == 'C', MSG); + ASSERT(rab.direct_name() == 'A', MSG); + ASSERT(rbc.direct_name() == 'B', MSG); + ASSERT(rcd.direct_name() == 'C', MSG); A &rac = c; B &rbd = d; - ASSERT(rac.virtual_name() == '?', MSG); - ASSERT(rbd.virtual_name() == '?', MSG); - ASSERT(rac.direct_name() == '?', MSG); - ASSERT(rbd.direct_name() == '?', MSG); + ASSERT(rac.virtual_name() == 'C', MSG); + ASSERT(rbd.virtual_name() == 'C', MSG); + ASSERT(rac.direct_name() == 'A', MSG); + ASSERT(rbd.direct_name() == 'B', MSG); A &rad = d; - ASSERT(rad.virtual_name() == '?', MSG); - ASSERT(rad.direct_name() == '?', MSG); + ASSERT(rad.virtual_name() == 'C', MSG); + ASSERT(rad.direct_name() == 'A', MSG); return 0; } diff --git a/exercises/19_class_virtual_destruct/main.cpp b/exercises/19_class_virtual_destruct/main.cpp index cdd54f74f..982e32d10 100644 --- a/exercises/19_class_virtual_destruct/main.cpp +++ b/exercises/19_class_virtual_destruct/main.cpp @@ -5,22 +5,22 @@ struct A { // TODO: 正确初始化静态字段 - static int num_a = 0; + static int num_a; A() { ++num_a; } - ~A() { + virtual ~A() { --num_a; } - + virtual char name() const { return 'A'; } }; struct B final : public A { // TODO: 正确初始化静态字段 - static int num_b = 0; + static int num_b; B() { ++num_b; @@ -34,13 +34,16 @@ struct B final : public A { } }; +int A::num_a = 0; +int B::num_b = 0; + int main(int argc, char **argv) { auto a = new A; auto b = new B; - ASSERT(A::num_a == ?, "Fill in the correct value for A::num_a"); - ASSERT(B::num_b == ?, "Fill in the correct value for B::num_b"); - ASSERT(a->name() == '?', "Fill in the correct value for a->name()"); - ASSERT(b->name() == '?', "Fill in the correct value for b->name()"); + ASSERT(A::num_a == 2, "Fill in the correct value for A::num_a"); + ASSERT(B::num_b == 1, "Fill in the correct value for B::num_b"); + ASSERT(a->name() == 'A', "Fill in the correct value for a->name()"); + ASSERT(b->name() == 'B', "Fill in the correct value for b->name()"); delete a; delete b; @@ -48,13 +51,13 @@ int main(int argc, char **argv) { ASSERT(B::num_b == 0, "Every B was destroyed"); A *ab = new B;// 派生类指针可以随意转换为基类指针 - ASSERT(A::num_a == ?, "Fill in the correct value for A::num_a"); - ASSERT(B::num_b == ?, "Fill in the correct value for B::num_b"); - ASSERT(ab->name() == '?', "Fill in the correct value for ab->name()"); + ASSERT(A::num_a == 1, "Fill in the correct value for A::num_a"); + ASSERT(B::num_b == 1, "Fill in the correct value for B::num_b"); + ASSERT(ab->name() == 'B', "Fill in the correct value for ab->name()"); // TODO: 基类指针无法随意转换为派生类指针,补全正确的转换语句 - B &bb = *ab; - ASSERT(bb.name() == '?', "Fill in the correct value for bb->name()"); + B &bb = *static_cast(ab); + ASSERT(bb.name() == 'B', "Fill in the correct value for bb->name()"); // TODO: ---- 以下代码不要修改,通过改正类定义解决编译问题 ---- delete ab;// 通过指针可以删除指向的对象,即使是多态对象 diff --git a/exercises/20_function_template/main.cpp b/exercises/20_function_template/main.cpp index cb6d978d3..48718c7b6 100644 --- a/exercises/20_function_template/main.cpp +++ b/exercises/20_function_template/main.cpp @@ -2,7 +2,8 @@ // READ: 函数模板 // TODO: 将这个函数模板化 -int plus(int a, int b) { +template +T plus(T a, T b) { return a + b; } @@ -14,7 +15,7 @@ int main(int argc, char **argv) { ASSERT(plus(1.25f, 2.5f) == 3.75f, "Plus two float"); ASSERT(plus(1.25, 2.5) == 3.75, "Plus two double"); // TODO: 修改判断条件使测试通过 - ASSERT(plus(0.1, 0.2) == 0.3, "How to make this pass?"); + ASSERT(std::abs(plus(0.1, 0.2) - 0.3) < 1e-6, "How to make this pass?"); return 0; } diff --git a/exercises/21_runtime_datatype/main.cpp b/exercises/21_runtime_datatype/main.cpp index 9c4bf376a..c3d6e83e0 100644 --- a/exercises/21_runtime_datatype/main.cpp +++ b/exercises/21_runtime_datatype/main.cpp @@ -18,13 +18,19 @@ struct TaggedUnion { }; // TODO: 将这个函数模板化用于 sigmoid_dyn -float sigmoid(float x) { +template +T sigmoid(T x) { return 1 / (1 + std::exp(-x)); } TaggedUnion sigmoid_dyn(TaggedUnion x) { TaggedUnion ans{x.type}; // TODO: 根据 type 调用 sigmoid + if (x.type == DataType::Float) { + ans.f = sigmoid(x.f); + } else { + ans.d = sigmoid(x.d); + } return ans; } diff --git a/exercises/22_class_template/main.cpp b/exercises/22_class_template/main.cpp index d4985d904..8ba758eec 100644 --- a/exercises/22_class_template/main.cpp +++ b/exercises/22_class_template/main.cpp @@ -10,6 +10,10 @@ struct Tensor4D { Tensor4D(unsigned int const shape_[4], T const *data_) { unsigned int size = 1; // TODO: 填入正确的 shape 并计算 size + for (int i = 0; i < 4; ++i) { + shape[i] = shape_[i]; + size *= shape[i]; + } data = new T[size]; std::memcpy(data, data_, size * sizeof(T)); } @@ -28,6 +32,37 @@ struct Tensor4D { // 则 `this` 与 `others` 相加时,3 个形状为 `[1, 2, 1, 4]` 的子张量各自与 `others` 对应项相加。 Tensor4D &operator+=(Tensor4D const &others) { // TODO: 实现单向广播的加法 + unsigned int size = 1; + for (int i = 0; i < 4; ++i) size *= shape[i]; + + unsigned int strides[4]; + strides[3] = 1; + strides[2] = shape[3]; + strides[1] = shape[2] * strides[2]; + strides[0] = shape[1] * strides[1]; + + unsigned int other_strides[4]; + other_strides[3] = 1; + other_strides[2] = others.shape[3]; + other_strides[1] = others.shape[2] * other_strides[2]; + other_strides[0] = others.shape[1] * other_strides[1]; + + for (unsigned int i = 0; i < size; ++i) { + unsigned int coords[4]; + unsigned int idx = i; + for (int d = 0; d < 4; ++d) { + coords[d] = idx / strides[d]; + idx -= coords[d] * strides[d]; + } + + unsigned int other_idx = 0; + for (int d = 0; d < 4; ++d) { + if (others.shape[d] > 1) { + other_idx += coords[d] * other_strides[d]; + } + } + data[i] += others.data[other_idx]; + } return *this; } }; diff --git a/exercises/23_template_const/main.cpp b/exercises/23_template_const/main.cpp index e0105e168..2200d071f 100644 --- a/exercises/23_template_const/main.cpp +++ b/exercises/23_template_const/main.cpp @@ -11,6 +11,10 @@ struct Tensor { Tensor(unsigned int const shape_[N]) { unsigned int size = 1; // TODO: 填入正确的 shape 并计算 size + for (unsigned int i = 0; i < N; ++i) { + shape[i] = shape_[i]; + size *= shape[i]; + } data = new T[size]; std::memset(data, 0, size * sizeof(T)); } @@ -35,6 +39,11 @@ struct Tensor { for (unsigned int i = 0; i < N; ++i) { ASSERT(indices[i] < shape[i], "Invalid index"); // TODO: 计算 index + unsigned int stride = 1; + for (unsigned int j = i + 1; j < N; ++j) { + stride *= shape[j]; + } + index += indices[i] * stride; } return index; } diff --git a/exercises/24_std_array/main.cpp b/exercises/24_std_array/main.cpp index c29718d9d..1c99d7f5e 100644 --- a/exercises/24_std_array/main.cpp +++ b/exercises/24_std_array/main.cpp @@ -8,21 +8,21 @@ int main(int argc, char **argv) { { std::array arr{{1, 2, 3, 4, 5}}; - ASSERT(arr.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(arr) == ?, "Fill in the correct value."); + ASSERT(arr.size() == 5, "Fill in the correct value."); + ASSERT(sizeof(arr) == 20, "Fill in the correct value."); int ans[]{1, 2, 3, 4, 5}; - ASSERT(std::memcmp(arr.?, ans, ?) == 0, "Fill in the correct values."); + ASSERT(std::memcmp(arr.data(), ans, 20) == 0, "Fill in the correct values."); } { std::array arr; - ASSERT(arr.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(arr) == ?, "Fill in the correct value."); + ASSERT(arr.size() == 8, "Fill in the correct value."); + ASSERT(sizeof(arr) == 64, "Fill in the correct value."); } { std::array arr{"Hello, InfiniTensor!"}; - ASSERT(arr.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(arr) == ?, "Fill in the correct value."); - ASSERT(std::strcmp(arr.?, "Hello, InfiniTensor!") == 0, "Fill in the correct value."); + ASSERT(arr.size() == 21, "Fill in the correct value."); + ASSERT(sizeof(arr) == 21, "Fill in the correct value."); + ASSERT(std::strcmp(arr.data(), "Hello, InfiniTensor!") == 0, "Fill in the correct value."); } return 0; } diff --git a/exercises/25_std_vector/main.cpp b/exercises/25_std_vector/main.cpp index f9e41bb78..805635c37 100644 --- a/exercises/25_std_vector/main.cpp +++ b/exercises/25_std_vector/main.cpp @@ -8,81 +8,81 @@ int main(int argc, char **argv) { { std::vector vec{1, 2, 3, 4, 5}; - ASSERT(vec.size() == ?, "Fill in the correct value."); + ASSERT(vec.size() == 5, "Fill in the correct value."); // THINK: `std::vector` 的大小是什么意思?与什么有关? - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); int ans[]{1, 2, 3, 4, 5}; - ASSERT(std::memcmp(vec.?, ans, sizeof(ans)) == 0, "Fill in the correct values."); + ASSERT(std::memcmp(vec.data(), ans, sizeof(ans)) == 0, "Fill in the correct values."); } { std::vector vec{1, 2, 3, 4, 5}; { - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(vec.size() == 5, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); double ans[]{1, 2, 3, 4, 5}; - ASSERT(std::memcmp(vec.?, ans, sizeof(ans)) == 0, "Fill in the correct values."); + ASSERT(std::memcmp(vec.data(), ans, sizeof(ans)) == 0, "Fill in the correct values."); } { vec.push_back(6); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(vec.size() == 6, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); vec.pop_back(); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(vec.size() == 5, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); } { vec[4] = 6; - ASSERT(vec[0] == ?, "Fill in the correct value."); - ASSERT(vec[1] == ?, "Fill in the correct value."); - ASSERT(vec[2] == ?, "Fill in the correct value."); - ASSERT(vec[3] == ?, "Fill in the correct value."); - ASSERT(vec[4] == ?, "Fill in the correct value."); + ASSERT(vec[0] == 1, "Fill in the correct value."); + ASSERT(vec[1] == 2, "Fill in the correct value."); + ASSERT(vec[2] == 3, "Fill in the correct value."); + ASSERT(vec[3] == 4, "Fill in the correct value."); + ASSERT(vec[4] == 6, "Fill in the correct value."); } { // THINK: `std::vector` 插入删除的时间复杂度是什么? - vec.insert(?, 1.5); + vec.insert(vec.begin() + 1, 1.5); ASSERT((vec == std::vector{1, 1.5, 2, 3, 4, 6}), "Make this assertion pass."); - vec.erase(?); + vec.erase(vec.begin() + 3); ASSERT((vec == std::vector{1, 1.5, 2, 4, 6}), "Make this assertion pass."); } { vec.shrink_to_fit(); - ASSERT(vec.capacity() == ?, "Fill in the correct value."); + ASSERT(vec.capacity() == 5, "Fill in the correct value."); vec.clear(); ASSERT(vec.empty(), "`vec` is empty now."); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(vec.capacity() == ?, "Fill in the correct value."); + ASSERT(vec.size() == 0, "Fill in the correct value."); + ASSERT(vec.capacity() == 5, "Fill in the correct value."); } } { - std::vector vec(?, ?); // TODO: 调用正确的构造函数 + std::vector vec(48, 'z'); // TODO: 调用正确的构造函数 ASSERT(vec[0] == 'z', "Make this assertion pass."); ASSERT(vec[47] == 'z', "Make this assertion pass."); ASSERT(vec.size() == 48, "Make this assertion pass."); - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); { auto capacity = vec.capacity(); vec.resize(16); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(vec.capacity() == ?, "Fill in a correct identifier."); + ASSERT(vec.size() == 16, "Fill in the correct value."); + ASSERT(vec.capacity() == capacity, "Fill in a correct identifier."); } { vec.reserve(256); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(vec.capacity() == ?, "Fill in the correct value."); + ASSERT(vec.size() == 16, "Fill in the correct value."); + ASSERT(vec.capacity() == 256, "Fill in the correct value."); } { vec.push_back('a'); vec.push_back('b'); vec.push_back('c'); vec.push_back('d'); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(vec.capacity() == ?, "Fill in the correct value."); - ASSERT(vec[15] == ?, "Fill in the correct value."); - ASSERT(vec[?] == 'a', "Fill in the correct value."); - ASSERT(vec[?] == 'b', "Fill in the correct value."); - ASSERT(vec[?] == 'c', "Fill in the correct value."); - ASSERT(vec[?] == 'd', "Fill in the correct value."); + ASSERT(vec.size() == 20, "Fill in the correct value."); + ASSERT(vec.capacity() == 256, "Fill in the correct value."); + ASSERT(vec[15] == 'z', "Fill in the correct value."); + ASSERT(vec[16] == 'a', "Fill in the correct value."); + ASSERT(vec[17] == 'b', "Fill in the correct value."); + ASSERT(vec[18] == 'c', "Fill in the correct value."); + ASSERT(vec[19] == 'd', "Fill in the correct value."); } } diff --git a/exercises/26_std_vector_bool/main.cpp b/exercises/26_std_vector_bool/main.cpp index b4ab4f9c4..4729c78d7 100644 --- a/exercises/26_std_vector_bool/main.cpp +++ b/exercises/26_std_vector_bool/main.cpp @@ -6,29 +6,29 @@ // TODO: 将下列 `?` 替换为正确的代码 int main(int argc, char **argv) { - std::vector vec(?, ?);// TODO: 正确调用构造函数 + std::vector vec(100, true);// TODO: 正确调用构造函数 ASSERT(vec[0], "Make this assertion pass."); ASSERT(vec[99], "Make this assertion pass."); ASSERT(vec.size() == 100, "Make this assertion pass."); // NOTICE: 平台相关!注意 CI:Ubuntu 上的值。 std::cout << "sizeof(std::vector) = " << sizeof(std::vector) << std::endl; - ASSERT(sizeof(vec) == ?, "Fill in the correct value."); + ASSERT(sizeof(vec) == 24, "Fill in the correct value."); { vec[20] = false; - ASSERT(?vec[20], "Fill in `vec[20]` or `!vec[20]`."); + ASSERT(!vec[20], "Fill in `vec[20]` or `!vec[20]`."); } { vec.push_back(false); - ASSERT(vec.size() == ?, "Fill in the correct value."); - ASSERT(?vec[100], "Fill in `vec[100]` or `!vec[100]`."); + ASSERT(vec.size() == 101, "Fill in the correct value."); + ASSERT(!vec[100], "Fill in `vec[100]` or `!vec[100]`."); } { auto ref = vec[30]; - ASSERT(?ref, "Fill in `ref` or `!ref`"); + ASSERT(ref, "Fill in `ref` or `!ref`"); ref = false; - ASSERT(?ref, "Fill in `ref` or `!ref`"); + ASSERT(!ref, "Fill in `ref` or `!ref`"); // THINK: WHAT and WHY? - ASSERT(?vec[30], "Fill in `vec[30]` or `!vec[30]`."); + ASSERT(ref, "Fill in `vec[30]` or `!vec[30]`."); } return 0; } diff --git a/exercises/27_strides/main.cpp b/exercises/27_strides/main.cpp index baceaf2a9..4c8b5fcaf 100644 --- a/exercises/27_strides/main.cpp +++ b/exercises/27_strides/main.cpp @@ -18,6 +18,11 @@ std::vector strides(std::vector const &shape) { // TODO: 完成函数体,根据张量形状计算张量连续存储时的步长。 // READ: 逆向迭代器 std::vector::rbegin // 使用逆向迭代器可能可以简化代码 + udim stride = 1; + for (int i = shape.size() - 1; i >= 0; --i) { + strides[i] = stride; + stride *= shape[i]; + } return strides; } diff --git a/exercises/28_std_string/main.cpp b/exercises/28_std_string/main.cpp index d8b276274..5ca96a9ee 100644 --- a/exercises/28_std_string/main.cpp +++ b/exercises/28_std_string/main.cpp @@ -10,9 +10,9 @@ int main(int argc, char **argv) { auto world = "world"; // READ: `decltype` 表达式 // READ: `std::is_same_v` 元编程判别 - ASSERT((std::is_same_v), "Fill in the missing type."); - ASSERT((std::is_same_v), "Fill in the missing type."); + ASSERT((std::is_same_v), "Fill in the missing type."); + ASSERT((std::is_same_v), "Fill in the missing type."); // TODO: 将 `?` 替换为正确的字符串 - ASSERT(hello + ", " + world + '!' == "?", "Fill in the missing string."); + ASSERT(hello + ", " + world + '!' == "Hello, world!", "Fill in the missing string."); return 0; } diff --git a/exercises/29_std_map/main.cpp b/exercises/29_std_map/main.cpp index fcccca347..68122a5fc 100644 --- a/exercises/29_std_map/main.cpp +++ b/exercises/29_std_map/main.cpp @@ -7,11 +7,13 @@ template bool key_exists(std::map const &map, k const &key) { // TODO: 实现函数 + return map.find(key) != map.end(); } template void set(std::map &map, k key, v value) { // TODO: 实现函数 + map[key] = value; } // ---- 不要修改以下代码 ---- diff --git a/exercises/30_std_unique_ptr/main.cpp b/exercises/30_std_unique_ptr/main.cpp index 9b98b5794..25275e2d1 100644 --- a/exercises/30_std_unique_ptr/main.cpp +++ b/exercises/30_std_unique_ptr/main.cpp @@ -50,11 +50,11 @@ int main(int argc, char **argv) { // ---- 不要修改以上代码 ---- std::vector answers[]{ - {"fd"}, // TODO: 分析 problems[1] 中资源的生命周期,将记录填入 `std::vector` // NOTICE: 此题结果依赖对象析构逻辑,平台相关,提交时以 CI 实际运行平台为准 - {"", "", "", "", "", "", "", ""}, - {"", "", "", "", "", "", "", ""}, + {"fd"}, + {"ffr", "d"}, + {"r", "d", "d"}, }; // ---- 不要修改以下代码 ---- diff --git a/exercises/31_std_shared_ptr/main.cpp b/exercises/31_std_shared_ptr/main.cpp index febbbcc6f..d35134457 100644 --- a/exercises/31_std_shared_ptr/main.cpp +++ b/exercises/31_std_shared_ptr/main.cpp @@ -10,36 +10,36 @@ int main(int argc, char **argv) { std::shared_ptr ptrs[]{shared, shared, shared}; std::weak_ptr observer = shared; - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 4, ""); ptrs[0].reset(); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 3, ""); ptrs[1] = nullptr; - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 2, ""); ptrs[2] = std::make_shared(*shared); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 1, ""); ptrs[0] = shared; ptrs[1] = shared; ptrs[2] = std::move(shared); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 3, ""); std::ignore = std::move(ptrs[0]); ptrs[1] = std::move(ptrs[1]); ptrs[1] = std::move(ptrs[2]); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 2, ""); shared = observer.lock(); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 3, ""); shared = nullptr; for (auto &ptr : ptrs) ptr = nullptr; - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 0, ""); shared = observer.lock(); - ASSERT(observer.use_count() == ?, ""); + ASSERT(observer.use_count() == 0, ""); return 0; } diff --git a/exercises/32_std_transform/main.cpp b/exercises/32_std_transform/main.cpp index f4dc25a5c..2178bd35e 100644 --- a/exercises/32_std_transform/main.cpp +++ b/exercises/32_std_transform/main.cpp @@ -10,6 +10,9 @@ int main(int argc, char **argv) { std::vector val{8, 13, 21, 34, 55}; // TODO: 调用 `std::transform`,将 `v` 中的每个元素乘以 2,并转换为字符串,存入 `ans` // std::vector ans + std::vector ans; + std::transform(val.begin(), val.end(), std::back_inserter(ans), + [](int x) { return std::to_string(x * 2); }); ASSERT(ans.size() == val.size(), "ans size should be equal to val size"); ASSERT(ans[0] == "16", "ans[0] should be 16"); ASSERT(ans[1] == "26", "ans[1] should be 26"); diff --git a/exercises/33_std_accumulate/main.cpp b/exercises/33_std_accumulate/main.cpp index 6326929d5..1d0bb8bda 100644 --- a/exercises/33_std_accumulate/main.cpp +++ b/exercises/33_std_accumulate/main.cpp @@ -11,7 +11,7 @@ int main(int argc, char **argv) { // - 形状为 shape; // - 连续存储; // 的张量占用的字节数 - // int size = + int size = std::accumulate(shape, shape + 4, 1, std::multiplies()) * sizeof(DataType); ASSERT(size == 602112, "4x1x3x224x224 = 602112"); return 0; }