簡體   English   中英

C - 從文本文件讀取輸入(int、string、int、int)

[英]C - Read input from text file (int,string,int,int)

首先對任何英文錯誤感到抱歉。 所以,我在 a.txt 文件中有這些數據

Codigo,Produto,StockMinimo,StockAtual
1,Couro,300,1000
2,Tecido,250,2000
...

我想跳過第一行,只將整數讀入結構

我正在使用波紋管 function 來計算文件的行數:

int nrLinhasFicheiro(char *filename){
    char ch;
    FILE *file;
    file = fopen(filename, "r");
    int linhas = 0;
    if (file != NULL) {
         for (ch = getc(file); ch != EOF; ch = getc(file)) 
        if (ch == '\n')  
            linhas = linhas + 1; 
    }
    fclose(file);
    return linhas - 1;
}

而這個將文件讀取到結構“Stock”:

void carregarStock(Stock *stock, char *nomeFicheiro){
    int i = 0;
    int codigo; //stores "codigo" values
    char stringFake[40], *storeProduto; //variables to store first line and "Produto" string
    int minimo, quantidade;
    
    FILE *fp = fopen(nomeFicheiro, "r");
    
    int numeroLinhas = nrLinhasFicheiro(nomeFicheiro);
    
    if (fp != NULL){
       
        if(numeroLinhas >0){
            fscanf(fp, "%s",stringFake);//skip first line
            
            while(i< numeroLinhas){
                fscanf(fp, "%d,%s ,%d,%d", &codigo, storeProduto, &minimo, &quantidade);
                //fscanf(fp, "%d,%s %d,%d", &codigo, storeProduto, &minimo, &quantidade);  also tried this and don't work
                
                if(codigo==1){
                    stock->minStockCouro = minimo;
                    stock->couroStock = quantidade;
                }else if(codigo==2){
                    stock->minStockTecido = minimo;
                    stock->tecidoStock = quantidade;
                }else if(codigo==3){
                    stock->minStockBorracha = minimo;
                    stock->borrachaStock = quantidade;
                }else if(codigo==4){
                    stock->minStockCordoes = minimo;
                    stock->cordoesStock = quantidade;
                }else if(codigo==5){
                    stock->minStockPalmilhas = minimo;
                    stock->palmilhasStock = quantidade;
                }   
                i++;
            }
            
        }else{
            puts("Error");          
        }      
    }else{
        puts(MSG_ERRO_LER_FICHEIRO);
    }
    fclose(fp);
}

Function 打印結構:

void mostrarStock(Stock stock){
    puts("==============  Stock : =============\n");
    puts("Codigo | Produto | Stock Minimo | Stock Atual\n");
    printf("1\tCouro\t\t%d\t\t%d\n", stock.minStockCouro, stock.couroStock);
    printf("2\tTecido\t\t%d\t\t%d\n", stock.minStockTecido, stock.tecidoStock);
    printf("3\tBorracha\t%d\t\t%d\n", stock.minStockBorracha, stock.borrachaStock);
    printf("4\tCordões\t\t%d\t\t%d\n", stock.minStockCordoes, stock.cordoesStock);
    printf("5\tPalmilhas\t%d\t\t%d\n", stock.minStockPalmilhas, stock.palmilhasStock);

}   

這就是我在 main 中調用 function 的方式:

int main(int argc, char** argv) {
    
    char *nomeFicheiro1 = "tabela_stocks.txt";
    Stock stock;
    carregarStock(&stock, nomeFicheiro1);
    mostrarStock(stock);
    
    return (EXIT_SUCCESS);
}

打印結構的 function 不打印。 我猜錯誤在

fscanf(fp, "%d,%s ,%d,%d", &codigo, storeProduto, &minimo, &quantidade);

我究竟做錯了什么?

您可以創建一個助手 function 來從一行中讀出兩個整數。

bool get_two(FILE *stream, int* a, int* b) {
    return fscanf(stream, " %*[^,],%*[^,],%d,%d", a, b) == 2;
}

然后你只需要調用它 5 次。

例子:

#include <stdbool.h>
#include <stdio.h>

typedef struct {
    int couroStock;
    int minStockCouro;
    int tecidoStock;
    int minStockTecido;
    int borrachaStock;
    int minStockBorracha;
    int cordoesStock;
    int minStockCordoes;
    int palmilhasStock;
    int minStockPalmilhas;
} Stock;

bool get_two(FILE *stream, int* a, int* b) {
    return fscanf(stream, " %*[^,],%*[^,],%d,%d", a, b) == 2;
}

int main() {
    FILE *fp = fopen("tabela_stocks.txt", "r");
    if(fp) {
        Stock s;
        fscanf(fp, "%*[^\n]"); // skip first line

        if(get_two(fp, &s.couroStock, &s.minStockCouro) &&
           get_two(fp, &s.tecidoStock, &s.minStockTecido) &&
           get_two(fp, &s.borrachaStock, &s.minStockBorracha) &&
           get_two(fp, &s.cordoesStock, &s.minStockCordoes) &&
           get_two(fp, &s.palmilhasStock, &s.minStockPalmilhas))
        {
            printf("%d %d\n", s.couroStock, s.minStockCouro);
            printf("%d %d\n", s.tecidoStock, s.minStockTecido);
            printf("%d %d\n", s.borrachaStock, s.minStockBorracha);
            printf("%d %d\n", s.cordoesStock, s.minStockCordoes);
            printf("%d %d\n", s.couroStock, s.minStockCouro);
        }
        fclose(fp);
    }
}

如果tabela_stocks.txt包含

Codigo,Produto,StockMinimo,StockAtual
1,Couro,300,1000
2,Tecido,250,2000
3,Borracha,200,500
4,Cordões,500,2000
5,Palmilhas,500,1000

然后 output 將是

300 1000
250 2000
200 500
500 2000
300 1000

由於Stock struct中的不同股票之間有很多相似之處,您可以將其分解成更小的部分,並使struct包含一只股票的信息:

#include <stdbool.h>
#include <stdio.h>

typedef struct {
    int stock;
    int min_stock;
} Stock;

bool Stock_read(FILE *stream, Stock *s) {
    return fscanf(stream, " %*[^,],%*[^,],%d,%d", &s->stock, &s->min_stock) == 2;
}

void Stock_print(const Stock *s) {
    printf("%d %d\n", s->stock, s->min_stock);
}

有了它,您可以創建這樣的Stocks類型:

typedef struct {
    Stock Couro;
    Stock Tecido;
    Stock Borracha;
    Stock Cordoes;
    Stock Palmilhas;
} Stocks;

bool Stocks_read(FILE *stream, Stocks *s) {
    return
        Stock_read(stream, &s->Couro) &&
        Stock_read(stream, &s->Tecido) &&
        Stock_read(stream, &s->Borracha) &&
        Stock_read(stream, &s->Cordoes) &&
        Stock_read(stream, &s->Palmilhas);
}

void Stocks_print(const Stocks *s) {
    Stock_print(&s->Couro);
    Stock_print(&s->Tecido);
    Stock_print(&s->Borracha);
    Stock_print(&s->Cordoes);
    Stock_print(&s->Palmilhas);
}

閱讀和打印會變得更簡單:

int main() {
    FILE *fp = fopen("tabela_stocks.txt", "r");
    if(fp) {
        Stocks s;
        fscanf(fp, "%*[^\n]"); // skip first line

        if(Stocks_read(fp, &s)) {
            Stocks_print(&s);
        }
        fclose(fp);
    }
}

仔細觀察Stocks struct ,您可能需要考慮使用數組:

typedef struct {
    Stock stocks[5];
} Stocks;

這也將簡化代碼的 rest,因為您可以遍歷該數組以讀取和打印每個Stock

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM