项目 #0 - C++ 入门

要将您的项目发布到公开的 Github 仓库上。

概述

本学期所有的编程项目都将基于 BusTub 数据库管理系统。该系统使用 C++ 编写。为了确保您具备必要的 C++ 基础,您必须完成一个简单的编程作业来评估您对基本 C++ 特性的了解。本项目不会给您评分,但您必须以满分完成本项目才能继续本课程的学习。任何无法在截止日期前完成此作业的学生将被要求退课。

本编程作业中的所有代码必须使用 C++ 编写。项目将专门为 C++17 编写,但我们发现通常了解 C++11 就足够了。如果您之前没有使用过 C++,以下是一些可以帮助您的资源:

如果您使用 VSCode,我们建议您安装 CMake ToolsC/C++ Extension Packclangd。之后,按照本教程学习如何在 VSCode 中使用可视化调试器:Debug a C++ project in VS Code

如果您使用 CLion,我们建议您按照本教程操作:CLion Debugger Fundamentals

如果您更喜欢使用 gdb 进行调试,有很多教程可以教您如何使用 gdb。以下是一些我们认为有用的教程:

这是一个个人项目,需要独立完成(即不分组)。

项目规格说明

考虑以下场景:您是一个热门博客网站的管理员,并且一直收到关于某些会计垃圾邮件过度泛滥的报告。为了绘制整体网络使用情况并检测潜在的 DDoS 攻击,您需要一种实时方法来计算每个 IP 地址在传入请求流中出现的频率。然而,流量非常庞大,这使得传统数据结构要么太慢,要么太耗内存。这就是 Count-Min Sketch 发挥作用的地方!

Count-min sketch(CM Sketch)是一种概率型数据结构,使用亚线性内存来近似数据流中项目的频率计数。它维护一个紧凑的二维计数器数组,由 d 个独立种子哈希函数寻址。每次更新在每行递增一个单元格,查询则返回这些计数器的最小值。此外,count-min sketch 是可合并的,意味着两个 sketch 的和等价于在相应输入流的拼接上构建单个 sketch。Count-min sketch 广泛用于网络流量监控、流分析和数据库系统优化。

Count-min sketch 基于以下参数:

为了解释该数据结构的工作原理,让我们按照开头的示例,考虑以下输入流:["24.156.99.202", "172.217.22.14", "64.104.78.227", "24.156.99.202"]。让我们使用宽度为 4、深度为 3 的 count-min sketch。对于 3 行中的每一行,对字符串进行哈希处理(使用该行的种子)以生成一个整数,对其取模 4 得到列索引,并递增 (行, 列) 处的计数器。

首先,将哈希矩阵(3 行 x 4 列)初始化为全零:

0 0 0 0
0 0 0 0
0 0 0 0

现在处理流。我们首先插入 "24.156.99.202"。假设以下哈希位置(mod 4):

我们相应地更新单元格:

0 0 1 0
1 0 0 0
0 0 0 1

接下来,我们插入 "172.217.22.14" 并在以下哈希位置递增计数器:

更新:

0 1 1 0
2 0 0 0
0 0 1 1

现在我们插入 "64.104.78.227":

表格变为:

0 1 1 1
2 1 0 0
0 0 2 1

最后,重复 "24.156.99.202"(与之前相同的哈希位置:2, 0, 3)。再次递增这些单元格:

0 1 2 1
3 1 0 0
0 0 2 2

现在,让我们估计 "24.156.99.202" 的频率。让我们查找插入该键时使用的相同列:

估计值为各行中的最小值:

Estimate("24.156.99.202") = min(2, 3, 2) = 2

为什么取最小值?每行的计数器可能因与其他项目的冲突而膨胀,但独立哈希行中的最小值给出了对真实频率的最紧上界。

资源

要更多了解 Count-min sketch 及其工作原理,

说明

您需要完成本项目的以下任务:

任务 #1

实现一个基本的 Count-min sketch 数据结构,支持插入、计数估计和合并。

count_min_sketch.h 中,需要实现以下函数:

您可以自由设计辅助函数来辅助实现。

重要信息

创建您自己的项目仓库

如果以下 git 概念(例如仓库、合并、拉取、分叉)对您来说不太清楚,请先花一些时间学习 git

按照说明设置您自己的私有仓库和开发分支。如果您之前通过 GitHub 界面(点击 Fork)分叉了仓库,请不要将任何代码推送到您公开的分叉仓库!在 git push 任何代码之前,请确保您的仓库是私有的。

如果教师对代码进行了任何更改,您可以通过将私有仓库连接到 CMU-DB 主仓库来合并更改到您的代码中。执行以下命令添加远程源:

$ git remote add public https://github.com/cmu-db/bustub.git

然后您可以在学期期间根据需要拉取最新的更改:

$ git fetch public
$ git merge public/master

设置您的开发环境

首先安装 BusTub 所需的软件包:

# Linux
$ sudo build_support/packages.sh
# macOS
$ build_support/packages.sh

请参阅 README 获取有关如何设置不同操作系统环境的更多信息。

要从命令行构建系统,请执行以下命令:

$ mkdir build
$ cd build
$ cmake -DCMAKE_BUILD_TYPE=Debug ..
$ make -j`nproc`

我们建议始终以调试模式配置 CMake。这将使您能够输出调试消息并检查内存泄漏(更多内容见以下部分)。

测试

您可以使用我们的测试框架来测试本次作业的各个组件。我们使用 GTest 进行单元测试。您可以通过在测试名称前添加 DISABLED_ 前缀来禁用 GTest 中的测试。要从命令行运行测试:

$ cd build
$ make -j$(nproc) count_min_sketch_test
$ ./test/count_min_sketch_test

在本项目中,没有隐藏的测试。在以后的项目中,起始代码中提供的测试只是我们用来评估和评分您项目的所有测试的子集。您应该自行编写额外的测试用例来检查您实现的完整功能。

请确保您删除了测试名称中的 DISABLED_ 前缀,否则它们将不会运行!

格式化

您的代码必须遵循 Google C++ 风格指南。我们使用 Clang 自动检查您的源代码质量。如果您的提交未通过这些检查中的任何一项,您的项目成绩将为

执行以下命令检查您的语法。format 目标将自动修正您的代码。check-lintcheck-clang-tidy 目标将打印错误,您必须手动修复这些错误以符合我们的风格指南。

$ make format
$ make check-clang-tidy-p0

内存泄漏

在本项目中,我们使用 LLVM Address Sanitizer (ASAN) 和 Leak Sanitizer (LSAN) 来检查内存错误。要启用 ASAN 和 LSAN,请以调试模式配置 CMake 并照常运行测试。如果存在内存错误,您将看到内存错误报告。请注意,macOS 仅支持地址检测器而不支持泄漏检测器

在某些情况下,地址检测器可能会影响调试器的可用性。在这种情况下,您可能需要通过以下方式配置 CMake 项目来禁用所有检测器:

$ cmake -DCMAKE_BUILD_TYPE=Debug -DBUSTUB_SANITIZER= ..

开发提示

您可以在调试模式下使用 BUSTUB_ASSERT 进行断言。请注意,BUSTUB_ASSERT 中的语句在发布模式下将不会被执行。 如果您需要在所有情况下进行断言,请使用 BUSTUB_ENSURE 代替。

我们将以发布模式测试您的实现。要以发布模式编译您的解决方案,

$ mkdir build_rel && cd build_rel
$ cmake -DCMAKE_BUILD_TYPE=Release ..

请将关于本项目的所有问题发布在 Piazza 上。 要直接给助教发邮件提问。

助教在本项目中不会查看您的代码或帮助您调试。

评分标准

为了通过本项目,您必须确保您的代码遵循以下准则:

  1. 提交是否成功执行了所有测试用例并产生了正确答案?
  2. 提交是否在没有内存泄漏的情况下执行?
  3. 提交是否遵循了代码格式化和风格策略?

请注意,在未来的项目中,我们将使用额外的测试用例来评分您的提交,这些测试用例比我们提供给您的示例测试用例更复杂。

迟交政策

本项目没有迟交天数。

提交

您将把实现提交到 Gradescope:

build 目录中运行此命令,它将创建一个名为 project0-submission.zipzip 归档文件,您可以将其提交到 Gradescope。

$ make submit-p0

虽然您可以随时多次提交答案,但您应将 Gradescope 作为您唯一的调试工具。大多数学生在截止日期前提交项目,因此 Gradescope 将需要更长的时间来处理请求。您可能无法及时获得反馈来帮助您调试问题。此外,Gradescope 的输出不太可能像调试器(如 gdb)的输出那样提供有用的信息,前提是您花了一些时间学习使用它。

CMU 学生应使用在 Piazza 上公布的 Gradescope 课程代码。

协作政策

警告:本项目的所有代码必须是您自己的。您不得从其他学生或网上找到的其他来源复制源代码。抄袭行为绝不被容忍。更多信息请参见 CMU 的学术诚信政策