0

これは、ソケットが作成され、受信したデータがテキスト ファイルに格納されるコードです。

// Initialize Winsock.
    cout << "connecting1\n";
    WSADATA wsadata;
    int iResult = WSAStartup (MAKEWORD(2,2), &wsadata );
    if (iResult !=NO_ERROR )
        printf("\nmyERROR at WSAStartup()\n");
    int sock = socket(AF_INET, SOCK_STREAM, 0);
    if (sock == -1) {
        perror("error opening socket"); return -1;
    }
    struct sockaddr_in sin;
    sin.sin_port = htons(port);
    sin.sin_addr.s_addr = inet_addr(host.c_str());
    sin.sin_family = AF_INET;

    if (connect(sock, (struct sockaddr *)&sin, sizeof(sin)) == -1) {
        perror("error connecting to host"); return -1;
    }
    const int query_len = query.length() + 1; // trailing '\0'
    if (send(sock, query.c_str(), query_len, 0) != query_len) {
        perror("error sending query"); return -1;
    }

    const int buf_size = 1024 * 1024;
    while (true) {
    std::vector<char> buf(buf_size, '\0');
    const int recv_len = recv(sock, &buf[0], buf_size - 1, 0);

    if (recv_len == -1) {
        perror("error receiving response"); return -1;
    } else if (recv_len == 0) {
        std::cout << std::endl; break; 
    } else {
       std::cout << &buf[0];
   fprintf(fp, "%s", &buf[0]);   // this lines writes to file
    }
}

ここでは、データはほとんど適切な形式で返されますが、場合によっては次のようになります。

{
  "type": "node",
  "id":

1000     // this 1000 is un-wanted

 1812432236,
  "lat": 20.2608987,
  "lon": 85.8379894
},

そのため、私のプログラムはこのノードを正しく解析できません。URLでクエリを書いている間、データは適切な形式で表示されます。また、プログラムを実行するたびにガベージ値が同じ場所に挿入されます。なぜこれが起こっているのでしょうか?

4

2 に答える 2

1

上記の質問により具体的なopenStreetMapヘルプフォーラムから回答を得ました...

そこに投稿した質問へのリンク

于 2013-01-30T09:22:31.650 に答える
0

recv 関数では、バッファーの文字ポインターを呼び出します。char buf[1024*1024] とは異なる、char のベクトルとして宣言された buffer があります。したがって、ファイルに出力すると、ベクトルはアイテムの構造の文字列を返していると思います。ベクトルには、文字を格納するための 1024*1024 サイズの連続したメモリではなく、タイプ char の 1024*1024 オブジェクトが含まれます。1024*1024 ベクトルには、個別の要素として格納されている chars オブジェクトが含まれていますが、メモリ内の連続的な割り当てとしては格納されていません。

std::vector buf(buf_size, '\0');に変更します to char buf[1024*1024]; 次に、recv を使用してデータを読み取る前にmemset(buf, 0, 1024*1024)を実行します。これで問題が解決すると思います (\0 をソケット経由でデータとして送信していないと仮定すると、文字列の終わりを示します。この場合、 %s はその時点でデータの出力を停止します)。

于 2013-01-30T07:10:33.757 に答える