- ベストアンサー
VC++2008Enterpriseでwinsockを使ったファイル送信時のゴミの除去方法について
- VC++2008Enterpriseでwinsockを使ってクライアント側からファイルを送信すると、ファイルの後ろにゴミがくっついてしまい、それを除去する方法がわかりません。
- サーバー側では問題なくファイルを受信し、出力することができますが、クライアント側だけゴミがついてしまいます。
- 送信するファイルはテキストファイルで中身は「aaa」「bbb」「111」といった内容です。クライアント側のソースコードにも問題はないように思いますが、どのようにすればゴミを除去できるのか教えてください。
- みんなの回答 (3)
- 専門家の回答
質問者が選んだベストアンサー
> これだと、何百行とか何千行のデータを送ることは出来なんですよね。 > このソースをこのようなデータに対応させることはできますか? recv()の戻りが0以下になるまでprintfを繰り返していますから、 基本的に今の受信処理構造で問題ありません。 (大量のデータはrecv()→printf()を何度も繰り返すことで処理できます。) ただし、 printf("%s\n",recv_buf); の\nが余計です。 printf("%s",recv_buf); が正しいです。 あと、 recv_buf[ok] = '\0'; を入れるなら、 ok = recv(s, recv_buf, sizeof(recv_buf),0); の部分は ok = recv(s, recv_buf, sizeof(recv_buf)-1,0); とする必要があります。 理由はわかりますよね?
その他の回答 (2)
- toda hiro(@hiro_knigh)
- ベストアンサー率39% (59/151)
> これだと、何百行とか何千行のデータを送ることは出来なんですよね。 > このソースをこのようなデータに対応させることはできますか? 近頃、非同期モードでしかプログラムした事が無かったので確かなことではありませんが、send関数は指定したデータを全て送る関数ではありません。 送信バッファに格納できた分だけデータを送る関数です。 遅れなかった分を送る(send)ようプログラムしなければなりません。 (一行が短かったらOKかな?) あと、winsockはストリームという考え方を取っていますので、recv関数での一行づつ受信と言うことはロジックを組まない限り出来ません。 が、提示されたプログラムを見るとサーバに送信するデータの元ネタはfgetsを使っていますので、'\n'が付加した形で送信されると思います。 単純に受信した内容をprintfすれば適切に改行されると思います。 ちなみに、上記理由により「printf("%s\n",recv_buf);」行の「\n」は削除した方が良いと判断します。
お礼
有難う御座いました。 そうですね、'\n'はいりまっせんでいした。 まだまだwinsockの知識が足らないと再実感しました。 perlで構成したソケットプログラムはうまくいったので、VCの方でも同じようにできるだろうと考えていたんですが、結果はごらんの通りで...
- toda hiro(@hiro_knigh)
- ベストアンサー率39% (59/151)
多分、recv_bufの後ろの部分がゴミとして表示されているのでしょう。 winsockのrecv関数はOK,NGだけでなく、受信したサイズを返すはずなので、一番最後のelseの直後に以下の一文を加えてみてはいかがでしょう。 recv_buf[ok] = '\0';
お礼
すごいです。有難う御座います。 一発で消えてしまいました。 たった一文で数時間の苦労が... もっと勉強しないとだめだなぁ。
補足
すいません。お手数をおかけしますが、質問させてください。 これだと、何百行とか何千行のデータを送ることは出来なんですよね。 このソースをこのようなデータに対応させることはできますか?
お礼
バッファであるrecv_bufのサイズぎりぎりまで読み込んだら'\0'を入れることができないからでしょうか。 まだまだ勉強しないといけないと、再実感しました。 けれど、まずは有難う御座いました。 とりあえず、3000件くらいの適当なテキストファイルを流してみましたが、無事通過しました。 ここに謝意を。