用C语言存储包含整数和字符的文件内容
我有一个文本文件用C语言存储包含整数和字符的文件内容,c,arrays,string,stdin,rpn,C,Arrays,String,Stdin,Rpn,我有一个文本文件input.txt,其内容如下: 12 3 / 2 3 - 3 4 * 1 2 4 + - 5 * 7 / 我的最终目标是读取文件的每一行并计算给定的RPN表达式。我编写了以下代码段,从stdin读取文件内容并将其存储在字符数组中: char expression[1000][256]; int i = 0; while (fgets(expression[i], 256, stdin)) { expression[i][strcspn(expression[i
input.txt
,其内容如下:
12 3 /
2 3 -
3 4 *
1 2 4 + - 5 * 7 /
我的最终目标是读取文件的每一行并计算给定的RPN表达式。我编写了以下代码段,从stdin读取文件内容并将其存储在字符数组中:
char expression[1000][256];
int i = 0;
while (fgets(expression[i], 256, stdin))
{
expression[i][strcspn(expression[i],"\r\n")] = 0;
i++;
}
现在,我有了数组中的所有行。我在这里的问题是,我想存储这些,这样就没有空格,每个数字(所有数字)或字符都在一个单独的索引中
例如,这里,
表达式[0][0]
是1,表达式[0][1]
是2。但是,我希望expression[0][0]
为12,expression[0][1]
为3,等等。到目前为止,您的示例做得很好!感谢您发布一个问题,解释您想要什么,并尝试解决它
您遇到的主要问题是,当您需要字符串数组时,您正在存储字符数组的数组(请记住字符串是字符*
)
我使用了[strtok][1]
方法,每当字符串碰到调用中列出的一个字符时,它都会拆分字符串(使用空字符)。然后分配内存,并将字符串复制到数组中
我编写了一些示例代码,就是这样做的
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char* expression[1000][256];
char buffer[256];
int line = 0;
while (fgets(buffer, 256, stdin)) {
int word = 0;
char* token = strtok(buffer, " \r\n");
do {
expression[line][word] = calloc(sizeof(char), strlen(token) + 1);
strcpy(expression[line][word], token);
word++;
} while ((token = strtok(NULL, " \r\n")) != NULL);
line++;;
}
printf("'%s', '%s', '%s'\n", expression[0][0], expression[0][1], expression[0][2]);
return 0;
}
#包括
#包括
#包括
int main(){
字符*表达式[1000][256];
字符缓冲区[256];
内线=0;
而(fgets(缓冲区,256,标准输入)){
int字=0;
char*token=strtok(缓冲区“\r\n”);
做{
表达式[line][word]=calloc(sizeof(char),strlen(token)+1);
strcpy(表达式[行][字],标记);
word++;
}而((token=strtok(NULL,“\r\n”)!=NULL);
行++;;
}
printf(“%s”、“s”、“s”\n)、表达式[0][0]、表达式[0][1]、表达式[0][2]);
返回0;
}
您可能不需要将整个文件存储在内存中,而是一次读取一行,计算并打印结果:
- 定义一个足以容纳一行输入的缓冲区
- 定义一个
int
数组用作RPN堆栈
- 在循环中,读取每行输入
- 在嵌套循环中,使用strtok
,解析令牌:
- 如果令牌是一个数字,则将其值推送到堆栈上
- 如果令牌是运算符,则在堆栈的前两个元素之间执行此操作,并在弹出它们后将结果存储到堆栈中
在行尾,打印堆栈顶部的值
您希望对堆栈溢出和下溢执行简单检查
下面是一个示例实现:
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char buffer[256];
int stack[sizeof(buffer) / 2]; // no need for stack overflow check
int i, sp, tos;
while (fgets(buffer, sizeof buffer, stdin)) {
char *p = buffer, *token, *q;
sp = -1;
stack[++sp] = 1;
stack[++sp] = 1;
while ((token = strtok(p, " \t\r\n")) != NULL) {
p = NULL;
tos = stack[sp];
if (!strcmp(token, "+")) {
stack[--sp] += tos;
} else
if (!strcmp(token, "-")) {
stack[--sp] -= tos;
} else
if (!strcmp(token, "*")) {
stack[--sp] *= tos;
} else
if (!strcmp(token, "/")) {
if (tos == 0 || (tos == -1 && stack[sp - 1] == INT_MAX)) {
printf("division overflow\n");
break;
}
stack[--sp] /= tos;
} else
if (!strcmp(token, "%")) {
if (tos == 0 || (tos == -1 && stack[sp - 1] == INT_MAX)) {
printf("division overflow\n");
break;
}
stack[--sp] %= tos;
} else {
tos = strtol(token, &q, 0);
if (q == token || *q != '\0') {
printf("invalid token: %s\n", token);
break;
}
stack[++sp] = tos;
}
if (sp < 2) {
printf("stack underflow for %s\n", token);
break;
}
}
if (token == NULL) {
for (i = 2; i <= sp; i++) {
printf("%d%c", stack[i], i == sp ? '\n' : ' ');
}
}
}
return 0;
}
输出:
4
-1
12
-3
使用fscanf
而不是fgets
。这是理解所读表达式所需的解析的一部分。如果数字是1234
,并且它不适合char
?也不能在1(expression[0][0]
)的空间中放置两个字符('1'
和'2'
)。。。不要使用fscanf
而不是fgets
。首选fgets()
后接sscanf()
。这适用于1000行,但当我使用5000+时,会出现分段错误。有什么方法可以防止这种情况发生吗?@fereydoon318:是的,有多种方法可以防止这种情况发生;一种是根本不存储每一行——只需在输入时处理每一行(例如,参见下面的chqrlie答案的相关方面);或者,您可以在阅读更多的输入行时动态分配内存——动态内存分配是C编程(以及其他语言)中的一个普遍需要,在线上有很多资源可以指导您;嗯
4
-1
12
-3