C Primer Plus ---- Chapter 11 ----Character Strings and String Functions -- 8. 练习题

C Primer Plus ---- Chapter 11 ----Character Strings and String Functions -- 8. 练习题

  1. Design and test a function that fetches the next n characters from input (including blanks, tabs, and newlines), storing the results in an array whose address is passed as an argument.
#include
#define LEN 10
char * getnchar(char * str, int n);
int main()
{
  char input[LEN];
  char *check;
  check = getnchar(input, LEN-1);
  if(check == NULL)
  puts("Input failed");
  else
  puts(input);
  puts("Done!");
  return 0;
}
char * getnchar(char *str, int n)
{
  int i, ch;
  for(i = 0; i < n; i++)
  {
    ch = getchar();
    if(ch != EOF)
    str[i] = ch;
    else
    break;
  }
  if (ch == EOF)
  return NULL;
  else
  {
    str[i] = '\0';
    return str;
  }
}

Answer



348sjdj-= jsjdji8


348sjdj
Done!
  1. Modify and test the function in exercise 1 so that it stops after n characters or after the
    first blank, tab, or newline, whichever comes first. (Don’t just use scanf().)
#include
#include
#define LEN 10
char * getnchar1(char *str, int n);
int main()
{
  char input[LEN];
  char *check;
  check = getnchar1(input, LEN-1);
  if(input[0] == '\0')
  puts("input failed");
  else
  puts(input);
  puts("Done!");
  return 0;

}
char *getnchar1(char *str, int n)
{
  int i,ch;
  for(i=0; i

Answer:


input failed
Done!
sdj23 sjdja
sdj23
Done!
  1. Design and test a function that reads the first word from a line of input into an array and discards the rest of the line. It should skip over leading whitespace. Define a word as a sequence of characters with no blanks, tabs, or newlines in it.
#include
#include
#define LEN 80
char *getword(char *str);
int main()
{
  char input[LEN];
 if(getword(input) != NULL)
  puts(input);
  puts("Done.");
  return 0;
}
char *getword(char *str)
{
 int ch;
 char *orig = str;
 while((ch = getchar()) != EOF && isspace(ch))
 continue;
 if(ch ==EOF)
 return NULL;
 else
 *str++ = ch;
 while((ch = getchar())!=EOF && !isspace(ch))
 *str++ = ch;
 *str = '\0';
 if(ch == EOF)
 return NULL;
 else
 while(getchar()!='\n')
 continue;
 return orig;
}

Answer:



 	ksj ds8sd8  8ds 
ksj
Done.
  1. Design and test a function like that described in Programming Exercise 3 except that it accepts a second parameter specifying the maximum number of characters that can be read.
#include
#include
#define LEN 80
char *getword(char *str,int n);
int main()
{
  char input[LEN];
 if(getword(input, LEN-1) != NULL)
  puts(input);
  puts("Done.");
  return 0;
}
char *getword(char *str,int n)
{
 int ch,i;
 char *orig = str;
 while((ch = getchar()) != EOF && isspace(ch))
 continue;
 if(ch ==EOF)
 return NULL;
 else
 {
   for (i=0; (!isspace(ch)) && (i
  1. Design and test a function that searches the string specified by the first function parameter for the first occurrence of a character specified by the second function parameter. Have the function return a pointer to the character if successful, and a null if the character is not found in the string. (This duplicates the way that the library strchr() function works.) Test the function in a complete program that uses a loop to provide input values for feeding to the function.
#include
#include
#define LEN 10
char *s_gets(char *st, int n);
char *mystrchr(char *st, char ch);
int main()
{
  char input[LEN];
  char *check;
  int ch;
  printf("Enter a string, enter a newline to quit: ");
  s_gets(input,LEN);
  while(input[0] != '\n')
  {
    printf("Enter a character for search: ");
    ch = getchar();
    while(getchar() != '\n')
    continue;
    check = mystrchr(input,ch);
    if (check == NULL)
    puts("search failed!");
    else
    puts(check);
    printf("Please enter another string, enter a newline to quit: ");
    s_gets(input,LEN);
  }
  puts("Bye!");
  return 0;
  }
  char *s_gets(char *s, int n)
  {
    char *ret_val;
    char *find;
    int ch,i;
    ret_val = fgets(s, n, stdin);
    if(ret_val)
    {
       find = strchr(s, '\n');
       if(find == NULL)
       while(getchar() != '\n')
       continue;
    }
    return ret_val;
  }
  char *mystrchr(char *st, char ch)
  {
    int find = 1;
    while(find)
    {
      while((*st != ch) && (*st != '\0'))
      st++;
      if(*st == '\0')
      {
        if(ch == '\0')
	{
	  return st;
	}
	else
	return NULL;
      }
      else
      {
       find = 0;
      }
    }
    return st;
  }
  1. Write a function called is_within() that takes a character and a string pointer as its two function parameters. Have the function return a nonzero value (true) if the character is in the string and zero (false) otherwise. Test the function in a complete program that uses a loop to provide input values for feeding to the function.
#include
#include
#include
#define LEN 10
_Bool is_within(const char *str, char ch);
char *s_gets(char *str, int n);
int main(void)
{
  char input[LEN];
  int ch;
  int found;
  while(s_gets(input,LEN) && input[0] != '\0')
  {
    printf("Please enter a character: ");
    ch = getchar();
    while(getchar() != '\n')
    continue;
    found = is_within(input, ch);
    if(found == 0)
    printf("%c not found in string.\n", ch);
    else
    printf("%c found in string %s.\n",ch, input);
    printf("Next string: ");
  }
  puts("Done.");
  return 0;
}
_Bool is_within(const char *str, char ch)
{
  while(*str != ch && *str != '\0')
  str++;
  return *str;
}
char *s_gets(char *str, int n)
{
  char *ret_val;
  char *find;
  ret_val = fgets(str, n, stdin);
  if(ret_val)
  {
    find = strchr(str, '\n');
    if(find)
    *find = '\0';
    else
    while(getchar() != '\n')
    continue;
  }
  return ret_val;
}

关于 _Bool 类型,根据博客C语言的布尔类型(_Bool)可知:
在 c99 新增的头文件里,增加了 stdbool.h ,定义如下:

#define bool	_Bool
#define true	1
#define false	0

_Bool类型长度为1,只能取值范围为0或1。将任意非零值赋值给_Bool类型,都会先转换为1,表示真。将零值赋值给_Bool类型,结果为0,表示假。

  1. The strncpy(s1,s2,n) function copies exactly n characters from s2 to s1, truncating s2 or padding it with extra null characters as necessary. The target string may not be null-terminated if the length of s2 is n or more. The function returns s1. Write your own version of this function; call it mystrncpy(). Test the function in a complete program that uses a loop to provide input values for feeding to the function.
#include
#include
#include
int input_int(void);
char *s_gets(char *s, int n);
char *mystrncpy(char *s1, char *s2, int n);
int main(void)
{
  char *s1, *s2;
  int len;
  printf("Enter the length of the string: ");
  len = input_int();
  printf("Please enter the string: ");
  while(s_gets(s2, len) && s2[0] != '\0')
  {
    s1 =(char*) malloc(len * sizeof(char));
    mystrncpy(s1, s2, len);
    printf("copyed string: %s\n",s1);
    free(s1);
    printf("Please enter the length of the string: ");
    len = input_int();
    printf("Enter next string, enter a newline to quit: ");
   }
   puts("Bye!");
   return 0;
}
int input_int(void)
{
  int n, status, ch;
  int flag = 1;
  while(flag)
  {
    status = scanf("%u",&n);
    if(status != 1)
    {
      printf("Please enter a positive integer: ");
      while(getchar() != '\n')
      continue;
      continue;
    }
    if(n <= 0)
    {
      printf("Please enter a positive integer: ");
      while(getchar() != '\n')
      continue;
      continue;
    }
    ch = getchar();
    if(ch != '\n')
    {
      printf("Please enter a positive integer: ");
      while(getchar() != '\n')
      continue;
      continue;
    }
    flag = 0;
    break;
  }
return n;
}
char *s_gets(char *str, int n)
{
  char *ret_val;
  char *find;
  ret_val = fgets(str, n, stdin);
  if(ret_val)
  {
  find = strchr(str, '\n');
  if(find)
  *find = '\0';
  else
  while(getchar() != '\n')
  continue;
  }
  return ret_val;
}
char *mystrncpy(char *s1, char *s2, int n)
{
  char *find;
  int i;
  find = s1;
  for(i=0; (i

Answer:

Enter the length of the string: d
Please enter a positive integer: 8u
Please enter a positive integer: 8 
Please enter the string: sdj sdjaliskd
copyed string: sdj sdj
Please enter the length of the string: s
Please enter a positive integer: 7
Enter next string, enter a newline to quit: 
Bye!

程序分析:
函数 int input_int(void); 用来输入一个正整数,表示字符串长度,排除输入字符,负数,小数,或者正整数后面还有其他非法字符的可能性。

  1. Write a function called string_in() that takes two string pointers as arguments. If the second string is contained in the first string, have the function return the address at which the contained string begins. For instance, string_in(“hats”, “at”) would return the address of the a in hats. Otherwise, have the function return the null pointer. Test the function in a complete program that uses a loop to provide input values for feeding to the function.
#include
#include
#define LEN 80
char *s_gets(char *s, int n);
char *string_in(const char*s1, const char *s2);
int main(void)
{
  char s1[LEN];
  char s2[LEN];
  char *pt;
  printf("Enter the target string:");
  s_gets(s1, LEN);
  printf("Enter the string for search:");
  while(s_gets(s2, LEN) && (s2[0] != '\0'))
  {
    pt = string_in(s1, s2);
    if(pt)
    {
      printf("string \"%s\" is found in string \"%s\".\n",s2,s1);
      puts(pt);
    }
    else
    puts("search failed");
    printf("Next string for searching, enter a newline to quit:");
  }
  puts("Bye!");
  return 0;
}
char *s_gets(char *s, int n)
{
  char *ret_val, *find;
  ret_val = fgets(s, n, stdin);
  if(ret_val)
  {
    find = strchr(s, '\n');
    if(find)
    *find = '\0';
    else
    while(getchar() != '\n')
    continue;
  }
  return ret_val;
}
char *string_in (const  char *s1, const char *s2)
{
  int n1, n2, i, flag;
  n1 = strlen(s1);
  n2 = strlen(s2);
  flag = 1;
  char *find;
  if(n1 < n2)
  return NULL;
  else
  {
    for(i=0; n1-n2-i >= 0; i++)
    {
      if(!strncmp((s1+i), s2, n2))
      {
       find = s1+i;
       flag = 0;
       return find;
      }
      
    }
    if(flag)
    return NULL;
  }
}

Answer

Enter the target string:sjdkjejsl skla;
Enter the string for search: 
string " " is found in string "sjdkjejsl skla;".
 skla;
Next string for searching, enter a newline to quit:js
string "js" is found in string "sjdkjejsl skla;".
jsl skla;
Next string for searching, enter a newline to quit:
Bye!
  1. Write a function that replaces the contents of a string with the string reversed. Test the function in a complete program that uses a loop to provide input values for feeding to the function.
#include
#include
#define LEN 40
char *s_gets(char *s, int n);
char *rev(char *str);
int main(void)
{
  char input[LEN];
  char *r;
  while(s_gets(input, LEN) && input[0] != '\0')
  {
    r = rev(input);
    if(rev)
    {
      printf("Reversed string:");
      puts(r);
    }
    else
    puts("failed");
    printf("Enter next string, enter a newline to quit:");
  }
  puts("Bye!");
  return 0;
}
char *s_gets(char *s, int n)
{
  char *ret_val;
  char *find;
  ret_val = fgets(s, n ,stdin);
  if(ret_val)
  {
    find = strchr(s, '\n');
    if(find)
      *find = '\0';
    else
    while(getchar()!='\n')
    continue;
  }
  return ret_val;
}
char *rev(char *str)
{
  char *pt;
   int i;
  int n = strlen(str);
  char ret[n+1];
  pt = str + n;
  for(i=0; i

Answer

sjs dksj
Reversed string:jskd sjs
Enter next string, enter a newline to quit: sj skd
Reversed string:dks js 
Enter next string, enter a newline to quit:
Bye!
  1. Write a function that takes a string as an argument and removes the spaces from the string. Test it in a program that uses a loop to read lines until you enter an empty line. The program should apply the function to each input string and display the result.
#include
#include
#define LEN 20
char *s_gets(char *s, int n);
char *remsp(char *str);
int main(void)
{
  printf("Enter a string:");
  char input[LEN];
  char *input1;
  while(s_gets(input, LEN) && input[0] != '\0')
  {
    input1 = remsp(input);
    printf("string removed spaces:");
    puts(input1);
    printf("Next string, enter a newline to quit:");
  }
  puts("Done.");
  return 0;
}
char *s_gets(char *s, int n)
{
  char *ret_val, *find;
  ret_val = fgets(s, n, stdin);
  if(ret_val)
  {
    find = strchr(s, '\n');
    if(find)
    *find = '\0';
    else
    while(getchar() != '\n')
    continue;
  }
  return ret_val;
}
char *remsp(char *str)
{
  int i, j, n;
  n = strlen(str);
  char ret[n+1];
  j = 0;
  for(i=0; i

Answer

Enter a string:sjd skjd
string removed spaces:sjdskjd
Next string, enter a newline to quit:sjd sjd
string removed spaces:sjdsjd
Next string, enter a newline to quit:dj lk slj lk
string removed spaces:djlksljlk
Next string, enter a newline to quit:
Done.
  1. Write a program that reads in up to 10 strings or to EOF, whichever comes first. Have it offer the user a menu with five choices: print the original list of strings, print the strings in ASCII collating sequence, print the strings in order of increasing length, print the strings in order of the length of the first word in the string, and quit. Have the menu recycle until the user enters the quit request. The program, of course, should actually
    perform the promised tasks.
#include
#include
#include
#define N 10
#define LEN 80
char *s_gets(char *s, int n);
int count_s(char *s[], int n);
void menu(void);
int choice_ch(void);
void Prints(char *s[], int n);
void Printa(char *s[], int n);
void Printlen(char *s[], int n);
int first_wlen(char *s);
void Printwlen(char *s[], int n);
int main(void)
{
  char *a[N];
  char ar[N][LEN];
  int i,row, opt;
  printf("Enter less than %d strings, enter newline to quit:\n", N+2);
  for(i=0; i 'E')
     {
      printf("Enter the corresponding option (case-insensitive): ");
      while(getchar() != '\n')
      continue;
      continue;
     }
     check = getchar();
     if(check != '\n')
     {
      printf("Enter the corresponding option (case-insensitive): ");
      while(getchar() != '\n')
      continue;
      continue;
     }
     flag = 0;
     break;
   }
   else
   {
      printf("Enter the corresponding option (case-insensitive): ");
      while(getchar() != '\n')
      continue;
      continue;
   }
 }
 return ch;
}
void Prints(char *s[], int n)
{
  int i;
  for(i=0; i strlen(s[k+1]))
       {
         temp = s[k];
	 s[k] = s[k+1];
	 s[k+1] = temp;
       }
     }
   }
  Prints(s, n);
}
int first_wlen(char *s)
{
   int i;
   for(i=0; i first_wlen(s[j+1]))
      {
        temp = s[j];
	s[j] = s[j+1];
	s[j+1] = temp;
      }
    }
  }
  Prints(s, n);
}
  1. Write a program that reads input up to EOF and reports the number of words, the number of uppercase letters, the number of lowercase letters, the number of punctuation characters, and the number of digits. Use the ctype.h family of functions.
#include
#include
#include
#define LEN 40
int main(void)
{
  int ch;
  int low_ct = 0;
  int up_ct = 0;
  int dig_ct = 0;
  int n_word = 0;
  int punc_ct = 0;
  bool inword = false;
  puts("Enter text to be analyzed (EOF to terminate):");
  while((ch = getchar()) != EOF)
  {
    if(islower(ch))
    low_ct++;
    else if(isupper(ch))
    up_ct++;
    else if (isdigit(ch))
    dig_ct++;
    else if(ispunct(ch))
    punc_ct++;
    if(!isspace(ch) && !inword)
    {
      inword = true;
      n_word++;
    }
    if(isspace(ch) && inword)
    inword = false;
  }
  printf("\nwords = %d, lowercase = %d, uppercase = %d,"
  "digits = %d, punctuation = %d\n",n_word, low_ct, up_ct, dig_ct,punc_ct);
  return 0;
}

程序分析:
输入知道遇到EOF,从键盘输入,除非按 Ctrl + d,否则不会结束输入。

  1. Write a program that echoes the command-line arguments in reverse word order. That is, if the command-line arguments are see you later, the program should print later you see.
#include
int main(int argc, char *argv[])
{
 int ct;
 for(ct = argc-1; ct > 0; ct--)
 printf("%s ",argv[ct]);
 printf("\n");
 return 0;
}

Answer

./13.o see you later
later you see 
  1. Write a power-law program that works on a command-line basis. The first command-line argument should be the type double number to be raised to a certain power, and the second argument should be the integer power.
//用pow()函数,且参数是变量时。编译时要用 -lm(link math.h),否则出错
//gcc -g 14.c -lm -o 14.o
#include 
#include 
#include 
int main(int argc, char *argv[])
{
  double num, exp, power;
  if(argc != 3)
  puts("Enter two numbers, enter again.");
  else
  {
    num = atof(argv[1]);
    exp = atof(argv[2]);
    if(num == 0.0 && exp == 0.0)
    printf("0 to the 0 pwoer doesn't exit.\n");
    else
    printf("%f to the %f power = %g \n", num, exp,pow(num,exp));
  }
  return 0;
}
  1. Use the character classification functions to prepare an implementation of atoi(); have this version return the value of 0 if the input string is not a pure number.
#include
#include
#include
#define LEN 10
char *s_gets(char *s, int n);
int myatoi(const char *str);
int main(void)
{
  char input[LEN];
  int n;
  printf("Enter string: ");
  while(s_gets(input, LEN) && input[0] != '\0')
  {
    n = myatoi(input);
    printf("string: %s, int: %d;\n",input, n);
    printf("Next strint: \n");
  }
  puts("Bye!");
  return 0;
}
char *s_gets(char *s, int n)
{
  char *ret, *find;
  ret = fgets(s, n, stdin);
  if(ret)
  {
    find = strchr(s, '\n');
    if(find)
    *find = '\0';
    else
    while(getchar() != '\n')
    continue;
  }
  return ret;
}
int myatoi(const char *str)
{
  int sign;
  int num = 0;
  while(isspace(*str))
  str++;
  sign = (*str == '-')? -1 : 1;
  if(*str == '-' || *str == '+')
  str++;
  for(; *str; str++)
  {
    if(isdigit(*str))
    num = num * 10 + *str - '0';
    else
    return 0;
  }
  return sign * num;
}

Answer

Enter string: 34s2
string: 34s2, int: 0;
Next strint: 
3.2
string: 3.2, int: 0;
Next strint: 
-2e3
string: -2e3, int: 0;
Next strint: 
332-1
string: 332-1, int: 0;
Next strint: 

Bye!
  1. Write a program that reads input until end-of-file and echoes it to the display. Have the program recognize and implement the following command-line arguments:
    -p Print input as is
    -u Map input to all uppercase
    -l Map input to all lowercase
    Also, if there are no command-line arguments, let the program behave as if the –p argument had been used
#include
#include
#include
int main(int argc, char *argv[])
{
  int ok = 0;
  int ch;
  char mode = 'p';
  if(argc == 2 && strlen(argv[1]) == 2 && argv[1][0] == '-')
  {
    if(argv[1][1] == 'p' || argv[1][1] == 'u' || argv[1][1] == 'l')
    {
      ok = 1;
      mode = argv[1][1];
    }
    else
    {
      printf("Usage: %s [-p | -u | -l]\n",argv[0]);
      return 0;
    }
  }
    else if(argc == 1)
    ok = 1;
    else
    {
      printf("Usage: %s [-p | -u | -l]\n",argv[0]);
      return 0;
    }
    if(ok)
    {
       while((ch = getchar()) != EOF) //按 ctrl + d 结束输入
       {
         switch(mode)
	 {
	   case 'p': putchar(ch); break;
	   case 'u': putchar(toupper(ch)); break;
	   case 'l': putchar(tolower(ch)); break;
	 }
       }
    }
    return 0;
  }

Answer

./16.o -usjejs8aj
SJEJS8AJ

你可能感兴趣的:(C,Primer,Plus)