CS144 Lab Checkpoint 1: stitching substrings into a byte stream

devtools/2025/3/6 19:24:39/

Putting substrings in sequence

TCP报文在发送方会被分成许多数据报文,传输中可能出现顺序的重排以及丢失和重发等现象,所以需要重装数据报文到原来字节流的顺序。

在本实验中,要实现的是重组器Reassembler,它接受子字符串和其中第一个字节的索引。流的每一个字节都有自己的索引,并从零开始计数。

What should the Reassembler store internally?

原则上,重组器必须处理三类知识:

  1. 流中的下一个字节。重组器一旦知道,立即将其推送到流。
  2. 在流的长度范围内但是暂时无法写入的字节。这些字节应该被存储在重组器中。
  3. 超出可用容量的字节。这些字节应该被丢弃。

在这里插入图片描述

本次要修改的文件是reassembler.hh和reassembler.cc,首先先在头文件中修改成员变量和构造函数如下

  size_t _capacity;                          std::vector<std::pair<char, bool>> _stream;size_t _cur_index;                          size_t _eof_index;                          size_t _unassembled_bytes_cnt;             

然后修改构造函数如下

  explicit Reassembler( ByteStream&& output ): output_( std::move( output ) ), _capacity( output.writer().available_capacity() ), _stream( output.writer().available_capacity() ), _cur_index( 0 ), _eof_index( std::numeric_limits<uint64_t>::max() ), _unassembled_bytes_cnt( 0 ){}

这里需要注意的一点是,相比较之前的实验代码,新版代码将Reader和Writer分离,我们需要通过Writer的available_capacity()去访问ByteStream的容量。
然后在reassembler.cc中修改如下,这里参考了CS144 Lab:Lab1 – LRL52 的博客 的博客的做法,他用vector存储pair对的方式,first元素存储字符,second元素存储是否被占用,这种处理方法很高效。

void Reassembler::insert( uint64_t first_index, string data, bool is_last_substring )
{// Your code here.// 首先确认要写入重组器的首末位置 uint64_t start = max( _cur_index, first_index );uint64_t end= min( first_index + data.size(), min( _cur_index + output_.writer().available_capacity(), _eof_index ) );// 如果是最后的子串,就记录结束下标if ( is_last_substring ) {_eof_index = min( _eof_index, first_index + data.size() );}// 写入重组器中for ( uint64_t i = start, j = start - first_index; i < end; i++, j++ ) {auto& t = _stream[i % _capacity];//如果重复出现的子串,前后不一致则报错if ( t.second == true ) {if ( t.first != data[j] )throw __throw_runtime_error;}// 之前没有占用的位置就将data对应位置的元素放入,然后重组器内的元素个数自增else {t = make_pair( data[j], true );++_unassembled_bytes_cnt;}}string str;// 将重组器中从_cur_index开始的直到终止下标或者是无效下标的元素写入字符串str中while ( _cur_index < _eof_index && _stream[_cur_index % _capacity].second == true ) {str.push_back( _stream[_cur_index % _capacity].first );// 一旦写入,重组器对应位置就要清空_stream[_cur_index % _capacity] = { 0, false };--_unassembled_bytes_cnt;++_cur_index;}// str输出到writeroutput_.writer().push( str );if ( _cur_index == _eof_index )output_.writer().close();
}// 返回还有多少字节存储在Reassembler中
uint64_t Reassembler::bytes_pending() const
{// Your code here.return _unassembled_bytes_cnt;
}

实验结果

在这里插入图片描述


http://www.ppmy.cn/devtools/165062.html

相关文章

iOS 使用消息转发机制实现多代理功能

在iOS开发中&#xff0c;我们有时候会用到多代理功能&#xff0c;比如我们列表的埋点事件&#xff0c;需要我们在列表的某个特定的时机进行埋点上报&#xff0c;我们当然可以用最常见的做法&#xff0c;就是设置代理实现代理方法&#xff0c;然后在对应的代理方法里面进行上报&…

电脑技巧:硬件检测工具 HWiNFO 8.16版本更新功能介绍

目录 一、版本8.16更新说明 二、安装说明 三、使用说明 HWiNFO是一个专业的系统信息检测工具&#xff0c;支持最新的技术和标准&#xff0c;可检查计算机硬件的所有信息。HWiNFO 主要可以显示出处理器、主板及芯片组、PCMCIA接口、BIOS版本、内存等信息&#xff0c;另外HWiN…

Kotlin语言特性(一):空安全、扩展函数与协程

Kotlin语言特性&#xff08;一&#xff09;&#xff1a;空安全、扩展函数与协程 一、引言 Kotlin作为Android官方推荐的开发语言&#xff0c;相比Java具有诸多现代化特性。本文将重点介绍Kotlin三个最具特色的语言特性&#xff1a;空安全、扩展函数和协程&#xff0c;并结合A…

DeepSeek集成到VScode工具,让编程更高效

DeepSeek与VScode的强强联合&#xff0c;为编程效率树立了新标杆。 DeepSeek&#xff0c;一款卓越的代码搜索引擎&#xff0c;以其精准的索引和高速的检索能力&#xff0c;助力开发者在浩瀚的代码海洋中迅速定位关键信息。 集成至VScode后&#xff0c;开发者无需离开熟悉的编辑…

物联网小范围高精度GPS使用

在园区内实现小范围高精度GPS&#xff08;全球定位系统&#xff09;定位&#xff0c;通常需要结合多种技术来弥补传统GPS在精度和覆盖范围上的不足。以下是实现小范围高精度GPS定位的解决方案&#xff0c;包括技术选择、系统设计和应用场景。 一、技术选择 在园区内实现高精度…

第一篇:Python基础入门

一、Python解释器安装全平台指南 1. Windows系统安装&#xff08;以Python 3.13.2为例&#xff09; 步骤详解&#xff1a; ​下载安装包​ 访问Python官网 → 选择"Windows" → 下载64位安装包&#xff08;如python-3.13.2-amd64.exe&#xff09; ​关键安装选项​…

直接法估计相机位姿

引入 在前面的文章&#xff1a;运动跟踪——Lucas-Kanade光流中&#xff0c;我们了解到特征点法存在一些缺陷&#xff0c;并且用光流法追踪像素点的运动来替代特征点法进行特征点匹配的过程来解决这些缺陷。而这篇文章要介绍的直接法则是通过计算特征点在下一时刻图像中的位置…

P10904 [蓝桥杯 2024 省 C] 挖矿

P10904 [蓝桥杯 2024 省 C] 挖矿 题目描述 小蓝正在数轴上挖矿&#xff0c;数轴上一共有 n n n 个矿洞&#xff0c;第 i i i 个矿洞的坐标为 a i a_i ai​。小蓝从 0 0 0 出发&#xff0c;每次可以向左或向右移动 1 1 1 的距离&#xff0c;当路过一个矿洞时&#xff0c;…