将"firstword secondword"从文本文件拉入单个字符数组
pull "firstword secondword" from text file into single char array
我在读取播放器文件时遇到分段错误:核心转储错误。。我正在尝试将"firstname lastname"添加到播放器结构中。我正在尝试访问"第0"个人并增加他们的名字,因为我需要第一个和最后一个,我不能像我对卡片值(未显示)"heart two 2"(例如)那样简单地在循环中fin>>people[I].name
// deck of cards
// below are initializations
#include <iostream>
#include <fstream>
#include <ctime>
#include <stdlib.h>
#include <string>
using namespace std;
//globals
const int maxCards = 52;
//Structs
struct card {
char suit[8];
char rank[6];
int cvalue;
char location;
};
struct player {
char name[];
int total;
card hand[];
};
//program
int main()
{
char tempfName[100];
char templName[100];
//create struct array(s)
card deck[52];
card shuffledDeck[52];
player people[4];
//set defalt values
for(int i=0;i<4;i++)
{
strcopy(people[i].name,"first last");
}
//open player names file
ifstream fin2;
string fin2Name;
//get file name from user
cout << "Enter player file name...(Players.txt)" << endl;
getline(cin,fin2Name);
fin2.open(fin2Name.c_str());
//check if Players.txt opens correctly
if(!fin2.good())
{
cout << "Error with player file!" << endl;
return 0;
}
else
{
int j =0;
//fin2 >> people[j].name; //prime file
while(fin2.good())
{
//find the length
int index =0, length=0;
while(tempfName[length] != ' ')
{
length++;
}
//now add space after first name
tempfName[length] = ' ';
length++;
while(templName[index] != ' ')
{
tempfName[length] = templName[index];
length++;
index++;
}
tempfName[length]=' ';
int counter =0;
while(templName[counter] != ' ')
{
people[0].name[counter] = templName[counter]; //testing program on "0th" people
counter++;
}
}
}
}
在结构中,name[]
和hand[]
的大小不确定。因此,很难从中解读出任何东西。
然后,一旦打开流,就要尝试确定单元化tempfName[]
的长度。这不好:你不确定它是null终止的,你会越界的!这就是你的segfault的起源。
考虑通过将它们声明为:来初始化它们
char tempfName[100]{};
char templName[100]{};
一旦修复了这一问题,您的代码仍然会在while (fin2.good())
上永远循环,而不会读取任何内容,并勇敢地在tempfName中添加一个空格,直到超出限制。
现在,假设您已经解决了所有这些问题,为name
设置一个长度,并取消对读取fin2 >> people[j].name;
的流的注释,那么您仍然会遇到非常危险的情况:如果数据比您之前看到的更长,它将被截断,并且名称不会有终止的"\0"。
建议1:
每当考虑存储字符串时,请考虑使用std::string而不是char[]。示例:
struct player {
string name = "first last" ; // initialisation value: no strcpy() needed !!
int total;
card hand[5]; // length ?
};
建议2:
循环使用流读取作为循环条件:
while (fin2 >> people[j].name) { ///!!!
...
j++; // don't foget to increment your counter
}
但是要小心,因为>>
一次读取一个字符串,该字符串以第一whilespace结尾(所以只有名字)。
如果你采用建议1,那么写起来就很容易了:
while (fin2 >> tempfName >> templName) { ///!!!
people[j++].name = tempfName + " " + templName;
}
它应该执行与循环几乎相同的事情,但指令和风险要少得多。
建议3:
如果你的玩家数量是固定的,定义最大常数,并使用for而不是一段时间来读取你的数据:
const int max_player = 4;
player people[max_player];
...
for (j=0; j<max_player && (fin2 >> people[j].name); j++) // instead of the former while
如果你的4的极限是arbirary,考虑使用向量。但现在这是另一回事了。
您的struct player
定义无效:
struct player {
char name[];
int total;
card hand[];
};
C字符串字段name
和hand
需要具有长度,例如
struct player {
char name[32];
int total;
card hand[32];
};
您的编译器应该为此给出一个错误("不完整类型")。
还要注意的是,由于您正在编写C++代码,因此最好使用std::string
而不是C风格的char *
字符串——这将更容易、更健壮,而且您不会混合使用C和C++习惯用法。
- 为什么我们将单个或多维数组的大小声明为常量值?
- 如何在 c++ 中将整个数组初始化为类构造函数中的单个元素
- 使用可变参数函数将整数和/或整数数组放入单个 int 数组中
- 使用一个内存集数组和单个堆栈在 O(n) 中查找数组的下一个更大元素
- 如何对文件中数组中的单个列进行冒泡排序?C++
- 将指向多维数组向量中的单个项的指针传递给函数 c++
- 如何将较大数字中从0到9的单个数字放入只包含数字的数组中
- 如何在 c++ 中将 2D 数组转换为单个字符串
- 尝试一次将单个字符读取到大小不确定的数组中
- 将嵌套的 std::arrays 视为具有链式 .data() 的单个平面数组
- 如何使用每个对象的单个构造函数参数动态分配C++对象数组?
- 如何在考虑对象切片的同时通过传入单个 Base 对象来打印出数组中的对象?
- 我如何处理数组的单个元素
- 从单个数组的不同段中初始化eigen ::向量
- 将类成员数组组合到单个数组时性能下降
- 在单个数组中与工作组及其大小合作
- 如何在单个数组中保存对象的动态数组
- 将包含单个数组的结构声明为packed有什么缺点吗
- 添加到单个数组元素-C++
- 在C++中将一个数组中的两个独立值存储到单个数组索引中