指定した行だけを読み込む方法

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
山口

指定した行だけを読み込む方法

#1

投稿記事 by 山口 » 15年前

120行近くあるテキストファイルがございます。
全部読みとるのでしたら出来るのですが
指定した行のみを取得する方法はないでしょうか?
出来れば引数に行数を入れるだけで戻り値が帰ってくるような関数にしたいです。

//test.txt
aiueo
kakikukeko
sasisuseso

//
char RetrunStrings( int num ){
char ch[16];

retrun ch
}

みたいな感じにしたいのですが・・・
説明が下手ですみません

バグ

Re:指定した行だけを読み込む方法

#2

投稿記事 by バグ » 15年前

不要な行を読み飛ばして、取得する行に来たらバッファにコピーしてやる感じでどうでしょう?
それと、関数の仕様ですが、引数で文字列バッファとサイズを渡した方がいいかと…

シエル

Re:指定した行だけを読み込む方法

#3

投稿記事 by シエル » 15年前

fgetsで指定した行数を読めばいいんじゃないでしょうか

初級者

Re:指定した行だけを読み込む方法

#4

投稿記事 by 初級者 » 15年前

読んだ行数を管理するための変数を用意する。

パコネコ

Re:指定した行だけを読み込む方法

#5

投稿記事 by パコネコ » 15年前

処理の無駄が多くていいなら、
for(a=0;a<n;a++)
fscanf(fp,"%s",&ch);
こんなのどうでしょう…よく使っているのですが…

それか、使ったことはないのですが…
fseek(fp,一行のバイト数*(行数-1),SEEK_SET);
これで指定したした行に行けると本で読んだのですが…あってますか?
ランダムアクセスっていうらしいのですが…勘違いならごめんなさい
============--
↑確かにバイト数が固定のときしか使えませんね…すいません
画像

softya

Re:指定した行だけを読み込む方法

#6

投稿記事 by softya » 15年前

fseek()で確かに指定したファイルの場所に行けますが、そのやり方だと一行のバイト数が固定の場合だけです。一行のサイズが可変だと順番に読むしか無いんですよね。
一度全部空読みして、それぞれの行のファイルの位置をftell()で得て配列に記録するなら2回目から早くなりますよ。

たかぎ

Re:指定した行だけを読み込む方法

#7

投稿記事 by たかぎ » 15年前

ちなみに、テキストファイルの場合、fseekで指定できるのは過去にftellで取得した位置だけです。
(厳密にいうと、SEEK_SETまたはSEEK_ENDを指定したときにオフセットを0にすることもできますが...)

できれば、いったん全部変数に読み込んでから操作するほうが簡単だと思います。
C++であれば、次のようにすれば、行単位でバラしながら簡単に読み込めます。

std::ifstream ifs(ファイル名);
std::vector<std::string> v;

while (!ifs)
{
std::string str;
std::getline(ifs, str);
v.push_back(str);
}

あとは、v[行番号 - 1] で簡単に指定行の内容を読み取れます。

バグ

Re:指定した行だけを読み込む方法

#8

投稿記事 by バグ » 15年前

毎回空読みするバージョンで作成してみました。
/*+++ 引 数 ++++++++++++++++++++++++++++++++++++++++++++++
      const char* path = ファイルパス
      const int   num  = 取得した行番号
            char* buf  = 取得データ格納先へのポインタ
      const int   size = バッファのサイズ(要素数)
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

+++++ 戻り値 ++++++++++++++++++++++++++++++++++++++++++++++
       0 = 正常終了
      -1 = ファイルオープン失敗
      -2 = 指定された行のデータ取得に失敗
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/
int ReturnStrings(const char* path, const int num, char* buf, const int size)
{
    int cnt = 0;
    FILE* file = NULL;

    if ((file = fopen(path, "r")) == NULL)
        return -1;

    while (fgets(buf, size, file) != NULL && num > ++cnt);
    fclose(file);

    if (num != cnt)
    {
        for (cnt = 0; cnt < size; ++cnt)
            buf[cnt] = 0;
        return -2;
    }

    return 0;
}

山口

Re:指定した行だけを読み込む方法

#9

投稿記事 by 山口 » 15年前

こんなにアドバイスを頂けるとは思いませんでした。
ありがとうございました。
やはり全部回すしかないのですね・・・。

>>バグ様
サンプルソースまでありがとうございます。
しかも私が一番作りたかった形(本当は戻り値ではなく直接値を変えたかった)で助かりました!!!

本当にありがとうございました。

同じような質問があるかもしれませんので動くソース(殆どバグ様が作ったのですが)を置いておきます。
#include <stdio.h>

int ReturnStrings(const char* path, const int num, char* buf, const int size)
{
    int cnt = 0;
    FILE* file = NULL;

    if ((file = fopen(path, "r")) == NULL)
        return -1;

    while (fgets(buf, size, file) != NULL && num > ++cnt);
    fclose(file);

    if (num != cnt)
    {
        for (cnt = 0; cnt < size; ++cnt)
            buf[cnt] = 0;
        return -2;
    }

    return 0;
}

void main( void ){
    char ch[128];
    ReturnStrings( "data.txt", 2, ch, 128 );
    printf( "%s", ch );
}

閉鎖

“C言語何でも質問掲示板” へ戻る