对于写入二进制文件的接口,void*/std::size\t函数参数对应该更改为什么? P> C++核心指南多次声明使用 >空> */COD>作为一个参数,最好是混淆,最坏的是容易出错。我最喜欢在结尾提到:

对于写入二进制文件的接口,void*/std::size\t函数参数对应该更改为什么? P> C++核心指南多次声明使用 >空> */COD>作为一个参数,最好是混淆,最坏的是容易出错。我最喜欢在结尾提到:,c++,C++,任何编写接收或返回void*的公共接口的人都应该大发雷霆。 这是我多年来个人最喜欢的一款。:) 也就是说: 为了符合此建议,此功能签名应更改为什么?目前,它适用于任何可以重新解释为常量字符*: bool writeBufferToFile(void* buffer, std::size_t size, const std::string& filePath) const { namespace FS = std::filesystem; FS::path p(filePa

任何编写接收或返回void*的公共接口的人都应该大发雷霆。 这是我多年来个人最喜欢的一款。:)

也就是说:

为了符合此建议,此功能签名应更改为什么?目前,它适用于任何可以重新解释为
常量字符*

bool writeBufferToFile(void* buffer, std::size_t size, const std::string& filePath) const
{
    namespace FS = std::filesystem;
    FS::path p(filePath);
    p.make_preferred();
    bool not_valid_path = FS::is_directory(p);
    bool invalid = not_valid_path;
    if(invalid) { return false; }

    std::ofstream ofs;
    ofs.open(p.string(), std::ios_base::binary);
    if(ofs)
    {
        ofs.write(reinterpret_cast<const char*>(buffer), size);
        return true;
    }
    return false;
}
bool writeBufferToFile(void*buffer,std::size\t size,const std::string和filePath)const
{
名称空间FS=std::filesystem;
路径p(filePath);
p、 使你更受欢迎;
bool not_valid_path=FS::is_目录(p);
bool invalid=无效路径;
if(无效){返回false;}
std::ofs流;
open(p.string(),std::ios_base::binary);
如果(ofs)
{
写入(重新解释转换(缓冲区),大小);
返回true;
}
返回false;
}

您需要的不是两个参数,一个指针和一个大小,而是一个表示二进制数据块的参数。在理想情况下,您可能会使用类似于
std::vector const&
,但问题是,如果调用方碰巧以其他方式存储数据,那么它会强制调用方执行分配/复制/释放

因此,您真正想要的是一个表示二进制数据块但不拥有该数据的类,它可以非常便宜地构造、复制和销毁,而不管底层数据是如何存储的。这避免了需要两个参数来表示一个概念

封装该类的类通常称为。因此,我建议:

class Slice
{
private:
    std::uint8_t const* data_;
    std::size_t size_;
  ...
};

bool writeBufferToFile (const Slice& data, const std::string& filePath) const
您的
切片
类可以很容易地从
std::vector
或几乎任何其他保存字节范围的合理方式构建。它可用作
void*
的类型安全替代品

激励性文章:

bool WriteBufferToFile(const std::any&buffer,std::size\t size,std::filesystem::path filepath)无异常{
名称空间FS=std::filesystem;
filepath=FS::绝对值(filepath);
filepath.make_preferred();
const auto not_valid_path=FS::is_目录(filepath);
const auto invalid=无效路径;
如果(无效){
返回false;
}
if(std::ofstreamofs{filepath,std::ios_base::binary};ofs.write(reinterpret_cast(&buffer),size)){
返回true;
}
返回false;
}

但这只是把问题转移到了一个问题上:这只是在地毯下面扫灰尘。漂亮盒子中的通用指针和大小仍然是通用指针和大小。该框不能解决任何问题。
std::uint8\u t
不能保证是某种字符类型,适合于别名任何类型。这可能是在某些方面platforms@n.m.它解决了需要在每个调用站点将单个对象(如向量、数组等)分解为两个对象,并且代码混乱的问题。有了适当的构造函数和其他代码,对
writeBufferToFile
的调用看起来到处都很干净,不会有参数不匹配的风险。@Casey如果没有更好的选择,您可以使用该构造函数。关键是提供更好的选择。(当然,你可能仍然需要与那些没有做出更好选择的人进行交互。)这是多余的,<代码>空白>代码>是有原因的。我相信你引用的评论是针对试图使用 Value*>代码的接口实现多态性的,C++有更好的和更安全的工具。在处理普通旧二进制数据的环境中,原始指针+大小是有意义的。只需查看最终完成工作的函数的签名:
basic\u ostream::write(const char\u type*s,std::streamsize count)