我正在浏览Chromium的源代码,以研究他们如何实现MediaRecorder API,该API将原始麦克风输入流编码/记录为特定格式。
我遇到了interesting codes from their source。简而言之:
matriu # matrix with cells in either state (0,1,2,3)
colors <- colorRampPalette(c("green", "red", "white", "blue"))
graph <- levelplot(matriu, col.regions = colors, cuts = 3)
print(graph)
因此,bool DoEncode(float* data_in, std::string* data_out) {
...
data_out->resize(MAX_DATA_BTYES_OR_SOMETHING);
opus_encode_float(
data_in,
reinterpret_cast<uint8_t*>(base::data(*data_out))
);
...
}
(C ++方法)在这里接受一个float数组并将其转换为编码的字节流,并且实际操作是在DoEncode
(这是一个纯C函数)中完成的。
有趣的部分是Google Chromium团队使用opus_encode_float()
而不是std::string
来存储字节数组,甚至将它们手动转换为uint8_t缓冲区。
为什么Google Chromium团队的成员会这样,并且有这样一种情况,对于通用字节缓冲区,使用std::vector<uint_8>
比使用std::string
这样的缓冲区更有用?
答案 0 :(得分:4)
Chromium编码样式(请参见下文)禁止无正当理由使用无符号整数类型。外部API不是这种原因。有符号和无符号字符的大小为1,为什么不这样。
我查看了opus编码器API,似乎早期版本使用的是签名char:
[out] data char*: Output payload (at least max_data_bytes long)
尽管API现在使用未签名的字符,但是描述仍然引用已签名的字符。因此,std::string
for chars对于较早的API更加方便,Chromium团队在更新API后并未更改已使用的容器,而是在一行中使用强制转换而不是在其他几行中进行更新。
整数类型
除非有正当的理由(例如表示位模式而不是数字),否则您不应使用诸如uint32_t
之类的无符号整数类型,或者您需要定义溢出模2^N
。特别是,请勿使用无符号类型来表示数字永远不会为负数。而是为此使用断言。
如果您的代码是一个返回大小的容器,请确保使用可容纳该容器的任何可能使用的类型。如有疑问,请使用较大的类型而不是较小的类型。
转换整数类型时要小心。整数转换和升级可能导致不确定的行为,从而导致安全漏洞和其他问题。
关于无符号整数
无符号整数非常适合表示位字段和模块化算术。由于历史上的意外,C ++标准还使用无符号整数来表示容器的大小-标准主体的许多成员认为这是一个错误,但实际上目前无法修复。无符号算术不能对简单整数的行为进行建模,而是由标准定义以对模块化算术进行建模(对上溢/下溢进行环绕),这一事实意味着编译器无法诊断出大量的错误。在其他情况下,定义的行为会阻碍优化。
也就是说,混合整数类型的符号性会导致同样大类的问题。我们可以提供的最佳建议:尝试使用迭代器和容器而不是指针和大小,尝试不混合有符号性,并避免使用无符号类型(表示位域或模块化算术除外)。不要仅使用无符号类型来断言变量是非负的。
答案 1 :(得分:1)
我们只能理论化。
我的推测:他们想使用std::string
中存在的内置SSO优化,但可能不适用于std::vector<uint8_t>
。