可变大小的char [] - 可以吗?

时间:2011-03-13 21:22:29

标签: c++ arrays variables size iso

请原谅我,如果这是愚蠢的,但我是C / C ++的新手。

在我正在创建的套接字库中,我的ClientSocket :: recv(int bufsize)函数使用'bufsize'初始化一个char []数组以从C套接字读入。给你用G ++编译的代码工作正常。

我遇到的问题是,正在编译我的代码的某些人收到以下错误: socket.cxx||In member function ‘std::string ClientSocket::recv(int)’:| socket.cxx|269|error: ISO C++ forbids variable length array ‘buffer’|

现在,从我在这个论坛上看到的是,微软只支持C89,而GCC支持C99,其中可变大小的数组是可接受的。同样在该线​​程上,他们建议使用_alloca() - 问题是,最多只支持1mb。我宁愿没有限制。

如果这是使其与GCC / MSVC ++交叉编译的唯一可行方法,我想我将不得不忍受它。知道一个替代方案会很高兴。像malloc()这样的东西有用吗? (以前从未使用它,所以我不知道)如果是这样,你能告诉我如何使用它或链接到教程/文档吗?谢谢!

P.S。:这是我的recv()函数的代码:

std::string ClientSocket::recv(int bufsize) {

    // isConnected() is a ClientSocket function
    if (!isConnected()) throw SocketException("Not connected.");

    char buffer[bufsize+1];

    // I did this because sometimes it was returning partial garbage :\
    memset(buffer, 0, bufsize);

    // the :: prefix means to call the recv() from the header files instead of ClientSocket::recv()
    int ret = ::recv(sockfd, buffer, bufsize-1, 0);

    if (ret < 0) {
        switch(errno) {
            case ECONNREFUSED:
                throw SocketException("Connection refused on recover.");
                break;
            case ENOTCONN:
                throw SocketException("Not connected.");
                break;
            default:
                throw SocketException("Unknown error reading socket.");
                break;
        }
    } else if (ret == 0) {
        // we got disconnected, return empty string. (connected is a protected variable of ClientSocket)
        connected = false;
        return "";
    }

    return buffer;
}

编辑:根据建议,我计划使用vector buffer(bufsize+1, 0); ... recv(sockfd, &buffer[0], bufsize, 0); ... return &buffer[0];char *buffer = new char[bufsize + 1]; memset(buffer, 0, bufsize); ... recv(sockfd, buffer, bufsize, 0); ... string tmp = buffer; delete [] buffer; return string(tmp); - 仍然安装MSVC ++以测试它,但我相信它会起作用。非常感谢! StackOverflow ROCKS!

4 个答案:

答案 0 :(得分:7)

g ++允许C ++中的C99可变长度数组作为语言扩展。

标准C ++不支持它们。

C ++中的

使用std::vectorstd::string

干杯&amp;第h。,

答案 1 :(得分:0)

尝试这样做:

char * buffer = new char[bufsize + 1];

答案 2 :(得分:0)

我会创建一个包含char *的简单缓冲类来处理这个问题。它将使用new来分配缓冲区。我相信也可以使用vector并且仍然符合标准。但我并不完全确定如何以推荐的方式解决这个问题。

答案 3 :(得分:0)

如果你使用gcc或g ++,你甚至不需要使用memset 你可以使用普通聚合将它全部分配给它 在char类型上,考虑一下:

char * buffer[bufsize+1] = {0};

此代码仅适用于gcc / g ++,因为gcc 允许堆栈上的可变大小的数组。

您唯一的选择是使用:

char * buffer = new char[bufsize+1];
// and assign it zeros with std::fill
std::fill(buffer, buffer+bufsize+1, 0);