如何使程序在 C 中处理不同的文本文件

How to make a program work on different text files in C

我正在尝试使用命令行参数并在 C 中解析文本文件。基本上我希望能够输入两个数字,例如 1 和 4,然后让它读取文本文件的一列将其打印到标准输出。我希望能够做这样的事情:

PID   TTY        TIME     CMD
449   ttys000    0:00.35 -bash
1129  ttys001    0:00.35 -bash
25605 ttys001    0:00.15  vi    prog.c
6132  ttys002    0:00.11 -bash
6208  ttys002    0:00.03  vi    test

然后做:

./your_prog 1 2 5 < data.txt 

PID   TTY
449   ttys000
1129  ttys001
25605 ttys001 prog.c
6132  ttys002 
6208  ttys002 test

我大部分时间都让程序能够根据命令行参数打印出正确的列。然而,我真正的问题是,如果我得到一个列数未知的文本文件并被要求处理它,我将如何让它在大多数(如果不是所有)这种格式的文本文件上工作?

这是我目前的代码:

#include <stdio.h>
#include <string.h>

int main(int argc, char **argv){
int col1, col2;
int size = 512;
char ch[size];
char *temp[size];
char *my_array[size];
int field_count = 0;

char *token;

if(argc == 1){
  fprintf(stderr, "I need more!\n");
  return 1;
}
else{
  //test to see what is stored
  int i;
  for (i = 0; i < argc; i++) {
    printf("argv[%d] = %s\n", i, argv[i]);   
  }

if(sscanf(argv[1], "%d", &col1) != 1) return 1;
if(sscanf(argv[2], "%d", &col2) != 1) return 1;   

while(fgets(ch, size, stdin) != NULL){
  //get 1st token
  token = strtok(ch, " ");
  while(token != NULL){
    //printf(" %s", token);
    temp[i++] = token;
    my_array[field_count] = token;
    field_count++;
    token = strtok(NULL, " ");
  } 
  if(col1 == 1){
    printf("%s\n", my_array[0]);
  }  
} 
  return 0;   
}
}

我注意到您正试图通过将从 strtok() 返回的指针存储在一个数组中来捕获该字段,但是该指针的数据是瞬态的:您需要一个字符串数组来将实际文本复制到.我已经修改并简化了您完成的尝试,请试试这个,它只打印捕获的字段 - 您的下一步可能是将它们写入文件。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define BUF_SIZE    512                     // for buffer size

void fatal(char *msg) {                     // easy  & informative getout
    printf("%s\n", msg);
    exit (1);
}

int main(int argc, char **argv){
    int col1, col2;
    char ch[BUF_SIZE];
    int field_count;
    char delims[] = " \t\n";                // might be tabs and newlines
    char *token;

    if(argc != 3)                           // check exact number of args
        fatal ("I need more!");
    if(sscanf(argv[1], "%d", &col1) != 1)
        fatal ("Bad first argument");
    if(sscanf(argv[2], "%d", &col2) != 1)
        fatal ("Bad second argument");
    printf("Capturing fields %d and %d\n", col1, col2);

    while(fgets(ch, BUF_SIZE, stdin) != NULL){
        field_count = 1;                    // reset field count
        printf("Fields captured:");
        token = strtok(ch, delims);
        while(token != NULL){
            if (field_count == col1 || field_count == col2)
                printf(" %s", token);
            field_count++;
            token = strtok(NULL, delims);
        }
        printf("\n");
    } 
    return 0;   
}