-1

一方では情報がファイルに書き込まれFILE*、他方では を使用して読み込まれるコードを処理する必要がありますifstream

元のコードと同じ動作を示すダミー コードをコンパイルしようとしました。

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <fstream>
#include <iostream>

int main()
{

    FILE* outFile = fopen("testFile", "w");  
    char* posBuf = NULL;                                                       
    unsigned int counter = 0;                           

    posBuf = (char*) malloc( sizeof(int) + 2*sizeof(double) );

    int iDummy = 123;
    memcpy(posBuf+counter, (const void*) &iDummy, sizeof(int));          
    counter += sizeof(int);                           

    double dDummy = 456.78;
    memcpy(posBuf+counter, (const void*) &dDummy, sizeof(double));            

    counter += sizeof(double);
    dDummy = 111.222;
    memcpy(posBuf+counter, (const void*) &dDummy, sizeof(double));            

    fputs(posBuf, outFile);   
    fclose(outFile);          

    /////////////////////

    std::ifstream myfile; 
    myfile.open("testFile", std::ios::in|std::ios::binary);

    myfile.seekg (0, std::ios::end);                        
    unsigned int length = myfile.tellg();              
    myfile.seekg (0, std::ios::beg);                        

    char* posBuf2 = (char*) malloc( length );           
    myfile.read(posBuf2, length);                       

    counter = 0;
    int idummy = 0;
    memcpy((void*) &idummy, posBuf2+counter, sizeof(int));  
    counter += sizeof(int);                                       
    printf("read integer: %u\n", idummy);            

    double ddummy = 1.0;
    memcpy((void*) &ddummy, posBuf2+counter, sizeof(double));                 
    counter += sizeof(double);                                       
    printf("read double: %f\n", ddummy);                                      

    ddummy = 1.0;
    memcpy((void*) &ddummy, posBuf2+counter, sizeof(double));                 
    counter += sizeof(double);                                       
    printf("read double: %f\n", ddummy);                                      

    myfile.close();

    /////////////////////

    FILE* inFile = fopen("testFile", "r");
    char* posBuf3 = NULL;

    unsigned int c = 0;
    while ( ! feof (inFile) )
    {
        posBuf3 = (char*) realloc((void*) posBuf3, c+4);
        fgets(posBuf3+c, 4, inFile);
        c += 4;
    }

    idummy = 0;
    memcpy((void*) &idummy, posBuf, sizeof(int));
    printf("read again integer: %u\n", idummy);

    ddummy =1.0;
    memcpy((void*) &ddummy, posBuf+sizeof(int), sizeof(double));
    printf("read again double: %f\n", ddummy);

    ddummy =1.0;
    memcpy((void*) &ddummy, posBuf+sizeof(int)+sizeof(double), sizeof(double));
    printf("read again double: %f\n", ddummy);

    return 0;
}

それから得られる出力は次のとおりです。

read integer: 123
read double: 0.000000
read double: 0.000000
read again integer: 123
read again double: 456.780000
read again double: 111.222000

ご覧のとおり、逆シリアル化FILE*は、ファイルの読み取りにも使用する場合にのみ機能します。

質問: その動作について何か説明はありますか?

ありがとう!

更新:

ifstream1)を使用して開くstd::ios::in|std::ios::binary

2) malloc を修正する

4

1 に答える 1

2

投稿されたコードに関するいくつかの問題:

  • 割り当てられたメモリの境界を超えて書き込みを行っていますposBuf(1intと 2doubleはメモリにコピーされますが、割り当てられるだけsizeof(int) + sizeof(double)です)。これは未定義の動作です。
  • fputs()引数を null で終了する文字列として扱うため、null 文字に遭遇すると書き込みを停止します。ファイルをバイナリ モードで開き、fwrite()入力をヌル終了文字列として扱わない代わりに使用します。

コードには他にもいくつかの問題があります。

  • それはCとC++の恐ろしい混合です
  • 回避可能な明示的な動的メモリ管理 (気malloc()にしないでrealloc()ください)。単純に次のように置き換えます。

    char posBuf[sizeof(int) + 2 * sizeof(double)];
    
  • while (!feof(inFile)).
  • I/O 操作の成功のチェックは事実上ありません。
于 2013-02-22T09:13:07.580 に答える