【问题标题】:_itoa_s doesn't accept dynamic array_itoa_s 不接受动态数组
【发布时间】:2022-01-12 19:26:52
【问题描述】:

我是 C++ 和动态内存分配的新手。

我有这段代码可以将数字从十进制转换为十六进制,它使用动态数组:

int hexLen = value.length();
char* arrayPtr = new char[hexLen];

_itoa_s(stoi(dec), arrayPtr, 16);

string hexVal = static_cast<string>(arrayPtr);

delete[] charArrayptr;

当我使用固定大小的数组时,_itoa_s() 使用它。但是,当使用动态数组时,编译器会说带有给定参数的方法不存在。

这是我做错了什么,还是_itoa_s() 根本不适用于动态数组?

带有非动态数组的版本(有效):

const int LENGTH = 20;
char hexCharArray[LENGTH];

_itoa_s(stoi(dec), hexCharArray, 16);

【问题讨论】:

  • 问题是为什么要使用_itoa_s?有更简单的方法可以转换为十六进制,而不必使用 new/delete。
  • 这可能只是 MRE,但如果大小是代码中的常量,则根本不需要动态数组。

标签: c++ arrays visual-c++ memory-management dynamic


【解决方案1】:

如果您仔细阅读documentation,您会发现您正在尝试调用_itoa_s() 的模板重载,它接受对固定大小数组的引用:

template <size_t size>
errno_t _itoa_s( int value, char (&buffer)[size], int radix ); 

您需要改为调用接受指针和大小的非模板重载:

errno_t _itoa_s( int value, char * buffer, size_t size, int radix );

试试这个:

int decValue = stoi(dec);

int hexLen = value.length();
int arraySize = hexLen + 1; // +1 for null terminator!

char* arrayPtr = new char[arraySize];

errno_t errCode = _itoa_s(decValue, arrayPtr, arraySize, 16);
if (errCode != 0)
{
    // error handling...
}
else
{
    string hexVal = arrayPtr;
    // use hexVal as needed...
}
delete[] charArrayptr;

由于您试图将十六进制转换为 string,因此您可以完全取消 char*

int decValue = stoi(dec);

string hexVal;
hexVal.resize(value.length());

errno_t errCode = _itoa_s(decValue, &hexVal[0], hexVal.size()+1, 16);
if (errCode != 0)
{
    // error handling...
}
else
{
    hexVal.resize(strlen(hexVal.c_str())); // truncate any unused portion
    // use hexVal as needed...
}

【讨论】:

    【解决方案2】:

    这就是我将十六进制转换为字符串的方式(C++ 20 和 C++20 之前的版本)

    #include <format> // C++20
    #include <string>
    #include <sstream>
    #include <iostream>
    
    int main()
    {
        int value = 123;
    
        // pre c++20 formatting
        std::ostringstream os;
        os << "0x" << std::hex << value << "n";
        std::cout << os.str();
    
        // c++20 formatting
        auto string = std::format("0x{:x}", value);
        std::cout << string;
    
        return 0;
    }
    

    【讨论】:

    • 我没有意识到你可以只使用这样的字符串流进行转换,谢谢。
    • 除了硬编码"0x"前缀,您也可以使用std::showbasestd::hexstd::ostringstream,并使用"{:#x}"作为std::format()
    • @MCSGaming 在(现代)C++ 中必须使用 new/delete 通常表明它可以以不同的方式完成。 isocpp.github.io/CppCoreGuidelines/CppCoreGuidelines,查看 P.3。执法
    猜你喜欢
    • 2021-11-13
    • 1970-01-01
    • 2019-07-20
    • 2015-05-26
    • 2020-12-20
    • 1970-01-01
    • 1970-01-01
    • 2015-11-27
    • 1970-01-01
    相关资源
    最近更新 更多