[C言語] ファイルに配列のデータを書き込む方法

C言語で配列のデータをファイルに書き込むには、まずファイルを開く必要があります。これにはfopen関数を使用し、書き込みモードでファイルを開きます。

次に、fprintffwrite関数を用いて配列のデータをファイルに書き込みます。fprintfはテキスト形式で、fwriteはバイナリ形式でデータを保存します。

最後に、fclose関数を使ってファイルを閉じ、リソースを解放します。これにより、配列のデータがファイルに保存されます。

この記事でわかること
  • fprintfとfwriteを用いたファイル書き込みの違いと使い方
  • バイナリファイルとテキストファイルの利点と選び方
  • 構造体配列や多次元配列のファイル書き込み方法
  • ファイルから配列データを読み込む方法
  • ファイル書き込み時のエラー対処法と動的メモリ管理の基礎

目次から探す

配列データのファイル書き込み

ファイルへの書き込み方法

配列データをファイルに書き込む方法は、主にfprintf関数fwrite関数を使用します。

それぞれの関数には特性があり、用途に応じて使い分けることが重要です。

fprintf関数の使用

fprintf関数は、テキスト形式でデータをファイルに書き込む際に使用します。

以下に、整数型の配列をテキストファイルに書き込む例を示します。

#include <stdio.h>
int main() {
    // 配列の定義
    int numbers[] = {1, 2, 3, 4, 5};
    // ファイルポインタの宣言
    FILE *file = fopen("output.txt", "w");
    
    // ファイルが開けたか確認
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    // 配列の要素をファイルに書き込む
    for (int i = 0; i < 5; i++) {
        fprintf(file, "%d\n", numbers[i]);
    }
    
    // ファイルを閉じる
    fclose(file);
    return 0;
}
output.txtの内容:
1
2
3
4
5

この例では、fprintf関数を使用して、配列の各要素をテキスト形式でファイルに書き込んでいます。

各要素は新しい行に書き込まれます。

fwrite関数の使用

fwrite関数は、バイナリ形式でデータをファイルに書き込む際に使用します。

以下に、同じ整数型の配列をバイナリファイルに書き込む例を示します。

#include <stdio.h>
int main() {
    // 配列の定義
    int numbers[] = {1, 2, 3, 4, 5};
    // ファイルポインタの宣言
    FILE *file = fopen("output.bin", "wb");
    
    // ファイルが開けたか確認
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    // 配列全体をファイルに書き込む
    fwrite(numbers, sizeof(int), 5, file);
    
    // ファイルを閉じる
    fclose(file);
    return 0;
}
output.binの内容はバイナリ形式で保存され、テキストエディタで開くと読み取れません。

この例では、fwrite関数を使用して、配列全体を一度にバイナリ形式でファイルに書き込んでいます。

バイナリ形式は、データのサイズが小さく、読み書きが高速であるという利点があります。

バイナリファイルとテキストファイル

ファイルにデータを書き込む際には、バイナリファイルとテキストファイルのどちらを使用するかを選択する必要があります。

それぞれの利点を理解して、適切な形式を選びましょう。

バイナリファイルの利点

  • 効率的なストレージ使用: バイナリ形式は、データをそのままの形式で保存するため、ストレージの使用量が少なくて済みます。
  • 高速な読み書き: バイナリデータはそのままメモリに読み込むことができるため、読み書きの速度が速いです。
  • データの精度保持: 浮動小数点数などの精度が必要なデータをそのまま保存できるため、精度の損失がありません。

テキストファイルの利点

  • 可読性: テキスト形式は人間が読みやすいため、デバッグやデータの確認が容易です。
  • 互換性: テキストファイルは多くのプラットフォームやアプリケーションでサポートされており、互換性が高いです。
  • 編集の容易さ: テキストエディタで簡単に編集できるため、データの修正が容易です。

用途に応じて、バイナリファイルとテキストファイルを使い分けることが重要です。

応用例

構造体配列の書き込み

構造体配列をファイルに書き込むことで、複雑なデータを効率的に保存することができます。

ここでは、構造体の定義からファイルへの書き込みまでを解説します。

構造体の定義と初期化

まず、構造体を定義し、配列として初期化します。

以下は、学生の情報を格納する構造体の例です。

#include <stdio.h>
// 学生情報を格納する構造体の定義
typedef struct {
    char name[50];
    int age;
    float gpa;
} Student;
int main() {
    // 構造体配列の初期化
    Student students[] = {
        {"田中太郎", 20, 3.5},
        {"鈴木花子", 22, 3.8},
        {"佐藤次郎", 19, 3.2}
    };
    return 0;
}

この例では、Studentという構造体を定義し、3人の学生の情報を初期化しています。

構造体配列のファイル書き込み

次に、構造体配列をファイルに書き込みます。

fwrite関数を使用して、バイナリ形式で書き込みます。

#include <stdio.h>
typedef struct {
    char name[50];
    int age;
    float gpa;
} Student;
int main() {
    Student students[] = {
        {"田中太郎", 20, 3.5},
        {"鈴木花子", 22, 3.8},
        {"佐藤次郎", 19, 3.2}
    };
    
    FILE *file = fopen("students.bin", "wb");
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    fwrite(students, sizeof(Student), 3, file);
    fclose(file);
    return 0;
}
students.binの内容はバイナリ形式で保存され、テキストエディタで開くと読み取れません。

この例では、fwrite関数を使用して、構造体配列全体をバイナリ形式でファイルに書き込んでいます。

多次元配列の書き込み

多次元配列をファイルに書き込むことで、行列や表形式のデータを保存することができます。

多次元配列の宣言

まず、多次元配列を宣言します。

以下は、整数型の2次元配列の例です。

#include <stdio.h>
int main() {
    // 2次元配列の宣言と初期化
    int matrix[3][3] = {
        {1, 2, 3},
        {4, 5, 6},
        {7, 8, 9}
    };
    return 0;
}

この例では、3×3の整数型の2次元配列を宣言し、初期化しています。

多次元配列のファイル書き込み

次に、多次元配列をファイルに書き込みます。

fwrite関数を使用して、バイナリ形式で書き込みます。

#include <stdio.h>
int main() {
    int matrix[3][3] = {
        {1, 2, 3},
        {4, 5, 6},
        {7, 8, 9}
    };
    
    FILE *file = fopen("matrix.bin", "wb");
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    fwrite(matrix, sizeof(int), 9, file);
    fclose(file);
    return 0;
}
matrix.binの内容はバイナリ形式で保存され、テキストエディタで開くと読み取れません。

この例では、fwrite関数を使用して、2次元配列全体をバイナリ形式でファイルに書き込んでいます。

ファイルからの配列データ読み込み

ファイルに保存された配列データを読み込むことで、プログラム内で再利用することができます。

fscanf関数の使用

fscanf関数を使用して、テキストファイルから配列データを読み込みます。

#include <stdio.h>
int main() {
    int numbers[5];
    FILE *file = fopen("output.txt", "r");
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    for (int i = 0; i < 5; i++) {
        fscanf(file, "%d", &numbers[i]);
    }
    
    fclose(file);
    
    // 読み込んだデータを表示
    for (int i = 0; i < 5; i++) {
        printf("%d\n", numbers[i]);
    }
    return 0;
}
1
2
3
4
5

この例では、fscanf関数を使用して、テキストファイルから整数型の配列データを読み込んでいます。

fread関数の使用

fread関数を使用して、バイナリファイルから配列データを読み込みます。

#include <stdio.h>
int main() {
    int numbers[5];
    FILE *file = fopen("output.bin", "rb");
    if (file == NULL) {
        printf("ファイルを開くことができませんでした。\n");
        return 1;
    }
    
    fread(numbers, sizeof(int), 5, file);
    fclose(file);
    
    // 読み込んだデータを表示
    for (int i = 0; i < 5; i++) {
        printf("%d\n", numbers[i]);
    }
    return 0;
}
1
2
3
4
5

この例では、fread関数を使用して、バイナリファイルから整数型の配列データを読み込んでいます。

バイナリ形式で保存されたデータをそのままメモリに読み込むため、効率的です。

よくある質問

fwriteとfprintfの違いは何ですか?

fwritefprintfは、どちらもファイルにデータを書き込むための関数ですが、用途と動作が異なります。

  • fwrite: バイナリ形式でデータをファイルに書き込みます。

データをそのままの形式で保存するため、効率的で高速です。

例:fwrite(buffer, sizeof(int), 5, file);

  • fprintf: テキスト形式でデータをファイルに書き込みます。

データを人間が読みやすい形式で保存するため、デバッグや確認が容易です。

例:fprintf(file, "%d\n", number);

ファイル書き込み時にエラーが発生した場合の対処法は?

ファイル書き込み時にエラーが発生した場合、以下の対処法を検討してください。

  1. ファイルポインタの確認: fopen関数の戻り値を確認し、NULLでないことを確認します。

例:if (file == NULL) { /* エラーハンドリング */ }

  1. 書き込み関数の戻り値の確認: fwritefprintfの戻り値を確認し、期待通りの値が返されているか確認します。
  2. エラーメッセージの表示: perror関数を使用して、エラーメッセージを表示します。

例:perror("ファイル書き込みエラー");

  1. ファイルのパスと権限の確認: ファイルのパスが正しいか、書き込み権限があるかを確認します。

配列のサイズを動的に変更することはできますか?

C言語では、配列のサイズを動的に変更することはできませんが、動的メモリ割り当てを使用して、配列のように扱うことができます。

  • malloc関数: 初期サイズのメモリを割り当てます。

例:int *array = (int *)malloc(initial_size * sizeof(int));

  • realloc関数: 既存のメモリブロックのサイズを変更します。

例:array = (int *)realloc(array, new_size * sizeof(int));

  • free関数: 使用後は必ずメモリを解放します。

例:free(array);

これにより、配列のサイズを動的に変更することが可能です。

まとめ

配列データをファイルに書き込む方法は、C言語プログラミングにおいて重要なスキルです。

この記事では、fprintffwriteを用いたファイル書き込みの方法、バイナリファイルとテキストファイルの利点、構造体や多次元配列の書き込み、そしてファイルからのデータ読み込みについて解説しました。

これらの知識を活用して、効率的なデータ管理を行い、プログラムの機能を拡張してみてください。

  • URLをコピーしました!
目次から探す