Opgaver i denne lektion   Gå til annoteret slide, hvor denne opgave er tilknyttet -- Tastaturgenvej: 'u'   Alfabetisk indeks   Kursets hjemmeside   

Opgaveløsning:
En simpel grep funktion


Her er en løsning på opgaven (som endvidere understøtter en -n option, der afstedkommer udskrift af linienumre):

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

#define MAXLINE 200

void grep(char *file_name, char* pattern, int print_line_numbers);

int main(int argc, char *argv[]) {

  char *pattern, *file_name;
  int line_numbers;  /* A boolean */

  /* Access the parameters of main */
  if (argc == 3) {
    file_name = argv[2]; line_numbers = 0; pattern = argv[1];
  }
  else if (argc == 4 && strcmp(argv[1], "-n") == 0) {
    file_name = argv[3]; line_numbers = 1; pattern = argv[2];
  }
  else {
    fprintf(stderr, "Calling form: search [-n] search_string file\n");
    exit(1);
  }

  grep(file_name, pattern, line_numbers);

  return 0;
}

/* Print those lines of file_name that contain pattern */
void grep(char *file_name, char* pattern, int print_line_numbers){  
  char line[MAXLINE];
  FILE *ifp;
  int n = 1;

  if ((ifp = fopen(file_name, "r")) == NULL){
    fprintf(stderr, "\nCannot open %s\n\n", file_name);
    exit(1);
  }

  while(fgets(line, MAXLINE, ifp) != NULL){
    if (strstr(line, pattern) != NULL){
      if (print_line_numbers)
        printf("%3i: %s", n, line);
      else
        printf("%s", line);
    }
    n++;
  }

  fclose(ifp);
}

Læg godt mærke til at vi ikke blot løser problemet i main. Vi skriver naturligvis en funktion, grep, som forsynes med passende parametre. I denne opgave kræves det, at grep funktionen udskriver tekst (linier med matchende tekststreng) på standard output.

Vi vil antage at programmet findes på kildefilen simple-grep.c. Oversættelse og kørsel (søgning i kildefilen selv) kan foregå på denne måde:

   > gcc simple-grep.c -o search
   > search.exe -n pattern simple-grep.c

Outputtet er:

  7: void grep(char *file_name, char* pattern, int print_line_numbers);
 11:   char *pattern, *file_name;
 16:     file_name = argv[2]; line_numbers = 0; pattern = argv[1];
 19:     file_name = argv[3]; line_numbers = 1; pattern = argv[2];
 26:   grep(file_name, pattern, line_numbers);
 31: /* Print those lines of file_name that contain pattern */
 32: void grep(char *file_name, char* pattern, int print_line_numbers){  
 43:     if (strstr(line, pattern) != NULL){

Dette output viser de linjer i kildefilen simple-grep.c (som vist ovenfor) der indholder ordet "pattern".