static_cast<字符*>和(字符*)之间的区别

Difference between static_cast<char*> and (char*)

本文关键字:字符 之间 区别 cast static gt lt      更新时间:2023-10-16

这是我的第一个问题:)

我有一个堆文件,我像下面这样打开它;

ifstream in ( filename,  ios :: binary | ios :: in ) 

然后,我希望在unsigned int hold中保存2字节的数据;

unsigned int hold;
in . read(static_cast<char *>(&hold), 2); 

对我来说似乎是正确的。但是,当我用

编译它时
g++  -ansi -pedantic-errors -Werror - -Wall  -o main main.cpp 

编译器发出错误

error: invalid static_cast from type ‘unsigned int*’ to type ‘char*’ 

实际上,我已经通过使用(char*)更改static_cast解决了这个问题,即

unsigned int hold;
in . read((char*)(&hold), 2); 

我的问题是:

  • static_cast<char*>(char*)的区别是什么?
  • 我不确定使用(char*)是否更安全。如果你有足够的知识,你能告诉我关于这个话题吗?

注:如果你有更好的想法,请帮助我,以便我可以改进我的问题。

static_cast是一种比隐式C风格强制转换更安全的强制转换。如果你试图将一个不兼容的实体强制转换为另一个实体,那么static_cast会给你一个编译时间错误,而不像隐式的c风格强制转换。

static_cast在这里给你一个错误,因为你想说的是采取int并尝试将其适合char,这是不可能的。int需要比char占用更多的内存,并且不能以安全的方式进行转换。

如果你仍然想实现这一点,你可以使用reinterpret_cast,它允许你类型转换两种完全不同的数据类型,但它不安全。
使用reinterpret_cast的唯一保证是,如果您将结果强制转换回原始类型,您将获得相同的值,但没有其他安全保证。

  • 首先-您可以轻松搜索_cast并找到任何c++强制转换。搜索c风格的强制转换要困难得多。
  • 第二—如果您使用c++强制转换,则需要选择正确的强制转换。在您的情况下,它是reinterpret_cast
    c风格的强制转换做了一切。

您也可以在这里查看:http://www.cplusplus.com/doc/tutorial/typecasting/了解不同c++类型转换的差异。我强烈建议只使用c++强制类型转换。这样你就可以很容易地找到&稍后再检查它们,你就会被迫思考自己到底在做什么。这提高了代码质量!

您应该使用reinterpret_cast<char *>而不是static_cast<char *>,因为数据类型不相关:您可以在指针之间转换子类到超类,例如,或在intlong之间,或在void *和任何指针之间,但unsigned int *char *不是"安全"的,因此您不能使用static_cast

区别在于c++中有各种类型的强制转换:

  • static_cast,用于"安全"转换;

  • reinterpret_cast用于"不安全"转换;

  • const_cast,用于删除const属性;

  • dynamic_cast用于向下转换(将指针/引用从超类转换为子类)。

C风格的强制转换(char *)x可以表示以上所有这些,因此它不像c++强制转换那样清晰。此外,搜索c++风格的强制转换很容易(只搜索_cast),但搜索所有C风格的强制转换相当困难。

这里的static_cast是非法的;你在不相关的人之间进行选择指针类型。使其编译的解决方案是使用reinterpret_cast(这是(char*)在本例中解析到的)。当然,这告诉你代码是不可移植的,事实上,除非你做的是一些非常低级的工作,否则可能行不通在所有情况下都正确。

在这种情况下,当然,您正在读取原始数据,并声明它是一个unsigned int。事实并非如此;读取输入的是原始数据,您可以仍然需要手动转换成任何你需要的,根据写入文件时使用的格式。)没有所谓的非格式化数据。仅包含未记录、未指定或未知格式。unformatted&rdquo的;输入和输出iostream被设计为读写你格式化的char缓冲区手动。这里需要reinterpret_cast是一个明确的警告你的代码有问题。(当然也有例外当然,但他们很少。)

在使用ifstream或ofstream或fstream进行二进制文件I/O时,通常会得到这些错误。问题是这些流的方法采用const char*,而你拥有的是其他类型的数组。您希望将数组以二进制位的形式写入到文件中。

这样做的传统方法是使用旧式的cast (char*),它基本上只是说,无论我把它当作(char*)的指针。迂腐/严格的模式不鼓励旧式的类型转换。为了消除这些警告,c++ 11的等效代码是reinterpret_cast<const char*>

我想说,如果你正在做二进制文件I/O,那么你已经知道东西可能是可移植的,也可能不是,这取决于你如何在一个操作系统中保存文件,并在另一个操作系统中读取。这完全是另一个问题,但是,不要被reinterpret_cast<const char*>吓到,因为这是你必须做的,如果你想写字节文件