已弃用字符串 const 的转换。到 wchar_t*
您好,我有一个泵类,需要使用一个成员变量,该变量是指向包含端口地址的 wchar_t 数组的指针,即:“com9”。
问题是,当我在构造函数中初始化此变量时,我的编译器会标记折旧转换警告。
pump::pump(){
this->portNumber = L"com9";}
这工作正常,但每次编译时的警告都很烦人,让我觉得我做错了什么。
我尝试创建一个数组,然后像这样设置成员变量:
pump::pump(){
wchar_t port[] = L"com9";
this->portNumber = port;}
但由于某种原因,这使我的 portNumber 指向“F”。
显然我的另一个概念问题。
感谢您对我的新手问题的帮助。
编辑:
根据请求, portNumber 的定义是:
class pump
{
private:
wchar_t* portNumber;
}
感谢答案,现在已更改为:
class pump
{
private:
const wchar_t* portNumber;
}
Hello I have a pump class that requires using a member variable that is a pointer to a wchar_t array containing the port address ie: "com9".
The problem is that when I initialise this variable in the constructor my compiler flags up a depreciated conversion warning.
pump::pump(){
this->portNumber = L"com9";}
This works fine but the warning every time I compile is anoying and makes me feel like I'm doing something wrong.
I tried creating an array and then setting the member variable like this:
pump::pump(){
wchar_t port[] = L"com9";
this->portNumber = port;}
But for some reason this makes my portNumber point at 'F'.
Clearly another conceptual problem on my part.
Thanks for help with my noobish questions.
EDIT:
As request the definition of portNumber was:
class pump
{
private:
wchar_t* portNumber;
}
Thanks to answers it has now been changed to:
class pump
{
private:
const wchar_t* portNumber;
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
如果
portNumber
是wchar_t*
,则它应该是const wchar_t*
。字符串文字是不可变的,因此元素是 const。存在从字符串文字到非常量指针的已弃用转换,但这很危险。进行更改,以便保持类型安全并且不使用不安全的转换。
第二个失败,因为您指向局部变量的内容。当构造函数完成时,变量消失并且您指向无效位置。使用它会导致未定义的行为。
最后,使用初始化列表:
初始化列表用于初始化,构造函数用于完成构造。 (此外,
this->
对于几乎所有 C++ 人来说都是丑陋的;它既不好又多余。)If
portNumber
is awchar_t*
, it should be aconst wchar_t*
.String literals are immutable, so the elements are
const
. There exists a deprecated conversion from string literal to non-const pointer, but that's dangerous. Make the change so you're keeping type safety and not using the unsafe conversion.The second one fails because you point to the contents of a local variable. When the constructor finishes, the variable goes away and you're pointing at an invalid location. Using it results in undefined behavior.
Lastly, use an initialization list:
The initialization list is to initialize, the constructor is to finish construction. (Also,
this->
is ugly to almost all C++ people; it's not nice and redundant.)使用 const wchar_t* 指向文字。
存在转换的原因是因为从 C 的早期版本开始,将字符串文字分配给非常量指针 [*] 是有效的。它被弃用的原因是修改文字是无效的,并且使用非常量指针来引用不得修改的内容是有风险的。
[*] C 最初没有
const
。当添加const
时,显然它应该适用于字符串文字,但是已经有代码在const
存在之前编写,如果突然必须撒上<,这些代码就会中断。 code>const 无处不在。时至今日,我们仍在为语言的重大改变付出代价。由于您使用的是 C++,因此这甚至不是对该语言的重大更改。Use
const wchar_t*
to point at a literal.The reason the conversion exists is because it has been valid from early versions of C to assign a string literal to a non-const pointer[*]. The reason it's deprecated is that it's invalid to modify a literal, and it's risky to use a non-const pointer to refer to something that must not be modified.
[*] C didn't originally have
const
. Whenconst
was added, clearly it should apply to string literals, but there was already code out there, written beforeconst
existed, that would break if suddenly you had to sprinkleconst
everywhere. We're still paying today for that breaking change to the language. Since it's C++ you're using, it wasn't even a breaking change to this language.显然,
portNumber
是一个wchar_t *
(非常量),对吗?如果是这样:第一个是错误的,因为字符串文字是只读的(它们是指向 char 数组的 const 指针通常存储在可执行文件的字符串表中,该数组映射在内存某处,通常在只读页面中)。
IIRC 批准了对非 const
char
s/wchar_t
s 的丑陋隐式转换,以实现与const
不使用时编写的旧代码的兼容性甚至不存在;遗憾的是,它让很多不知道 const 正确性意味着什么的白痴们编写了询问非 const 指针的代码,即使 const 指针是正确的选择。第二个是错误的,因为您使
portNumber
指向在堆栈上分配的变量,该变量在构造函数返回时被删除。构造函数返回后,存储在portNumber
中的指针指向随机垃圾。正确的做法是,如果不需要修改,将
portNumber
声明为const wchar_t *
。相反,如果它确实需要在类的生命周期内进行修改,通常最好的方法是完全避免 C 风格的字符串,而只是抛出一个std::wstring< /code>,它将处理与字符串相关的所有簿记。
Apparently,
portNumber
is awchar_t *
(non-const), correct? If so:the first one is wrong, because string literals are read-only (they are const pointers to an array of char usually stored in the string table of the executable, which is mapped in memory somewhere, often in a readonly page).
The ugly, implicit conversion to non-const
char
s/wchar_t
s was approved, IIRC, to achieve compatibility with old code written whenconst
didn't even existed; sadly, it let a lot of morons which do not know what const correctness means get away with writing code that asks non-const pointers even when const pointers would be the right choice.The second one is wrong because you're making
portNumber
point to a variable allocated on the stack, which is deleted when the constructor returns. After the constructor returns, the pointer stored inportNumber
points to random garbage.The correct approach is to declare
portNumber
asconst wchar_t *
if it doesn't need to be modified. If, instead, it does need to be modified during the lifetime of the class, usually the best approach is to avoid C-style strings at all and just throw in astd::wstring
, that will take care of all the bookkeeping associated with the string.