【问题标题】:Storing Pieces of a String using Strtok使用 Strtok 存储字符串的片段
【发布时间】:2023-03-10 07:30:02
【问题描述】:
#include <stdio.h>
#include <math.h>
#include <string.h>
int main(void)
{
    int menuswitch=1;
    int amountofstudents;
    int fname[50];
    int lname[50];
    int grade[50];
    int i;
    char studentinfo[100];
    printf("Enter Amount of Students: ");
    scanf("%d", &amountofstudents);
    for (i=0;i<amountofstudents;i++)
    {
        gets(studentinfo);
        strcpy(fname[i], strtok(studentinfo, " "));
        strcpy(lname[i], strtok(NULL, " "));
        strcpy(grade[i], strtok(NULL, " "));
    }

好吧,需要一点使用 strtok。我正在尝试存储输入字符串的片段以供以后排序。我正在考虑使用 strtok 来断开字符串,然后将每个部分放在相应的数组中。然而,每次我尝试时,我都会在 Visual Studios 中收到一个错误,说访问冲突。提前感谢您的帮助

错误是

First-chance exception at 0x5120F7B3 (msvcr110d.dll) in Lab 2.exe: 0xC0000005: Access violation reading location 0x00000000.
Unhandled exception at 0x5120F7B3 (msvcr110d.dll) in Lab 2.exe: 0xC0000005: Access violation reading location 0x00000000.

输入将是

FirstName Lastname 80(Grade)

【问题讨论】:

  • 您能否提供一些导致此问题的示例输入?也许还有来自调试器的调用堆栈?
  • 你为什么要将char*复制到int* vis strcpy?

标签: c arrays string strtok


【解决方案1】:

一个主要问题是您尝试复制到 整数值 而不是字符串。更改 整数数组到字符串数组:

...
char fname[50][100];
char lname[50][100];
char grade[50][100];
...

gets 函数也有问题(除了它已被废弃且不应使用),即先前的 scanf 没有从输入缓冲区中删除换行符,因此第一个 gets 调用将看到这个空的换行符并给你一个空行(你不检查)。

这可以通过告诉scanf 丢弃尾随空格来解决,方法是在"%d" 之后的格式字符串中添加一个空格:

scanf("%d ", &amountofstudents);
/*       ^    */
/*       |    */
/* Note space */

您应该使用fgets,而不是gets

fgets(studentinfo, sizeof(studentinfo), stdin);

最后,始终检查错误!

【讨论】:

  • 很抱歉将 int 放入一个菜鸟错误。 Fgets 确实解决了这个问题,谢谢,我将从现在开始使用它
【解决方案2】:

一个潜在的问题是scanf/gets combo。改用 fgets() 并在适当的时候使用 atoi() 转换为整数,对 strtok 返回的内容进行健全性检查也是很好的(假设任何关于输入的事情都不好) p>

char* token = strtok(studentinfo, " ");
if ( strlen(token) < sizeof(fname[i]) )
{
  strcpy(fname[i], token);
...

您还已将字符串声明为整数数组,它们应该是 char 例如char fname[50];

【讨论】:

    【解决方案3】:

    您遇到的问题是您已将三个变量(fname、lname 和grade)声明为 char[](数组)(嗯,这就是您要使用的类型),但您想提示并保留周围一堆学生资料。然后您尝试从 strtok() 复制到您想要成为 char[] 的内容,但是由于您取消引用 fname[i] (lname[i],grade[i]),它们是 char 类型,而不是 char []。

    您需要 stdlib.h 才能退出,

    #include <stdio.h>
    #include <stdlib.h> //for exit
    #include <string.h>
    //#include <math.h> //you don't need this, yet
    #define STUDLIMIT (100)
    

    您可以创建一个包含 fname[]、lname[]、grade[] 的数组(参见此处:http://www.cs.swarthmore.edu/~newhall/unixhelp/C_arrays.html),

    int main(void)
    {
        //int menuswitch=1; //you aren't using this
        int amountofstudents;
        char studentinfo[100];
        char fname[STUDLIMIT][50];
        char lname[STUDLIMIT][50];
        char grade[STUDLIMIT][50];
        int ndx;
        printf("Enter Amount of Students: ");
        if( (fscanf(stdin,"%d ", &amountofstudents)<=0)
        || (amountofstudents<1) || (amountofstudents>STUDLIMIT) )
        {
            printf("need %d to %d studends\n",1,STUDLIMIT); exit(0);
        }
        for (ndx=0;ndx<amountofstudents;ndx++)
        {
            printf("Student: "); fflush(stdout);
            fgets(studentinfo,sizeof(studentinfo),stdin);
            strcpy(fname[ndx], strtok(studentinfo, " "));
            strcpy(lname[ndx], strtok(NULL, " "));
            strcpy(grade[ndx], strtok(NULL, " "));
        }
    }
    

    或者您可以创建一个结构(ure)来保存输入的学生信息,并实例化这些学生记录的数组,为您输入和存储的每个学生创建一个数组,

    typedef struct student
    {
        char fname[50];
        char lname[50];
        char grade[50];
    } StudentObj;
    int StudentCopy(StudentObj*sp,char*fname,char*lname,char*grade)
    {
        if(!sp || !fname || !lname || !grade ) return -1;
        strcpy(sp->fname, fname);
        strcpy(sp->fname, lname);
        strcpy(sp->fname, grade);
    }
    StudentObj students[STUDLIMIT];
    int main(void)
    {
        //int menuswitch=1; //you aren't using this
        int amountofstudents;
        char studentinfo[100];
        char fname[50];
        char lname[50];
        char grade[50];
        int ndx;
        printf("Enter Amount of Students: ");
        if( (fscanf(stdin,"%d ",&amountofstudents)<=0)
        || (amountofstudents<1) || (amountofstudents>STUDLIMIT) )
        {
            printf("need %d to %d studends\n",1,STUDLIMIT); exit(0);
        }
        for (ndx=0;ndx<amountofstudents;ndx++)
        {
            printf("Student: "); fflush(stdout);
            fgets(studentinfo,sizeof(studentinfo),stdin);
            strcpy(fname, strtok(studentinfo, " "));
            strcpy(lname, strtok(NULL, " "));
            strcpy(grade, strtok(NULL, " \n\r"));
            StudentCopy(&(students[ndx]),fname,lname,grade);
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2021-02-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-12-07
      相关资源
      最近更新 更多