精华内容
下载资源
问答
  • (1)给定如下面形式的字符串:“ad,app,ai,apk”,"bed book bool bat byte"...把数字储存成字符串储存的就是数字字符,例如可以213以‘2’、‘1’、‘3’、‘\0’的形式储存一个字符串数组。而以...

    (1)给定如下面形式的字符串:“ad,app,ai,apk”,"bed book bool bat byte",它们由一组由固定字符隔开的字符串组合而成。

    如何将长字符串分割,即去掉其中的空格或逗号,使能够取出其中单个的字符串?

    (2)数字既能以字符串形式储存,也能以数值形式储存。把数字储存成字符串储存的就是数字字符,例如可以将213以‘2’、‘1’、‘3’、‘\0’的形式储存在一个字符串数组中。而以数值形式储存213,储存的是int类型的值。

    假设程序需要使用数值命令形参,但是命令形参被读取为字符串。因此,要使用数值必须先把字符串转换为数字。

    实例:这个txt文档中所有的SEED行是32个16进制数“0XAA”形式的文本,中间都以‘,’隔开,读取文件时数字以字符串形式储存,现需要取出SEED行所有的16进制数字的数值。


    下面的程序实现了将所有数值取出,并将这些数重新以16进制形式写入一个新的txt文档中,新的文档格式如下

    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #define SEEDNUM 10
    typedef struct {
    	char **str;     //the PChar of string array  
    	size_t num;     //the number of string  
    }IString;
    int Split(char *src, char *delim, IString* istr);
    
    int main(int argc, char *argv[])
    {
        FILE * sfp = NULL;
        FILE * ofp = NULL;
        sfp = fopen("10seed1122test.txt", "r");
    	ofp = fopen("10output1122.txt", "w");
    	
        if (NULL == sfp) /* 如果失败了 */
    	{
    		printf("错误!seed文件打开失败!");
    		exit(EXIT_FAILURE); /* 中止程序 */
    	}
    	if (NULL == ofp) /* 如果失败了 */
    	{
    		printf("错误!output文件打开失败!");
    		exit(EXIT_FAILURE); /* 中止程序 */
    	}
    	
    	int i;
    	long value[32];
    	char * end;
    	unsigned char tem_buf[1024];
    	unsigned char dest_buf[1024];
    	
    	for ( i = 0; i < SEEDNUM * 2; i++)
    
    	{
    		unsigned char output[32];
    		fgets(tem_buf, 1024, sfp);
    		if (i % 2)
    		{
    			strncpy(dest_buf, tem_buf + 5, 161);
    
    			IString istr;
    			Split(dest_buf, ",", &istr);
    			
    			int j;
    			unsigned char tem[32];
    			for (j = 0; j < 32; j++)
    			{
    				char dest[2];
    				strncpy(dest, istr.str[j] + 2, 2);
    				value[j] = strtol(dest, &end, 16);
    				fprintf(ofp,"%02X",value[j]);
    	
    			}
    			fprintf(ofp, "\n");
    		}
    	}
        return 0;
    }
    
    int Split(char *src, char *delim, IString* istr)//split buf  
    {
    	int i;
    	char *str = NULL, *p = NULL;
    
    	(*istr).num = 1;
    	str = (char*)calloc(strlen(src) + 1, sizeof(char));
    	if (str == NULL) return 0;
    	(*istr).str = (char**)calloc(1, sizeof(char *));
    	if ((*istr).str == NULL) return 0;
    	strcpy(str, src);
    
    	p = strtok(str, delim);
    	(*istr).str[0] = (char*)calloc(strlen(p) + 1, sizeof(char));
    	if ((*istr).str[0] == NULL) return 0;
    	strcpy((*istr).str[0], p);
    	for (i = 1; p = strtok(NULL, delim); i++)
    	{
    		(*istr).num++;
    		(*istr).str = (char**)realloc((*istr).str, (i + 1)*sizeof(char *));
    		if ((*istr).str == NULL) return 0;
    		(*istr).str[i] = (char*)calloc(strlen(p) + 1, sizeof(char));
    		if ((*istr).str[0] == NULL) return 0;
    		strcpy((*istr).str[i], p);
    	}
    	free(str);
    	str = p = NULL;
    
    	return 1;
    }

    此外,使用string.h库里的strtok函数也能用于分割字符串,strtok函数的用法有点不寻常,参考以下程序,可以达到与上面程序相同的效果。

    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #define SEEDNUM 10
    int main (void)
    {
    	const char * delim = ",";
    
    	FILE * sfp = NULL;
        FILE * ofp = NULL;
        sfp = fopen("10seed1122test.txt", "r");
    	ofp = fopen("strtok10output1122.txt", "w");
    	
    	if (NULL == sfp) /* 如果失败了 */
    	{
    		printf("错误!seed文件打开失败!");
    		exit(EXIT_FAILURE); /* 中止程序 */
    	}
    	if (NULL == ofp) /* 如果失败了 */
    	{
    		printf("错误!output文件打开失败!");
    		exit(EXIT_FAILURE); /* 中止程序 */
    	}
    	
    	int i;
    	for (i=0;i<SEEDNUM*2;i++)
    	{
    		char *pt;
    		char tem_buf[512];
    		fgets (tem_buf,512,sfp);
    		if (i%2)
    		{
    			pt = strtok(tem_buf+5,delim);
    			int j;
    			for(j=0; j<32 && pt; j++)
    			{
    				long value[32];
    				char *temp;
    				char *end;
    				temp = pt+2;
    				value[j] = strtol(temp, &end, 16);
    				fprintf(ofp,"%02X",value[j]);
    				pt = strtok(NULL,delim);
    			}
    			fprintf(ofp,"\n");
    		}
    	}
    	
    	return 0;
    }






    展开全文
  • 从键盘输入一个包含数字字符的字符串,从中取出符合双精度常量格式的数字字符串,并转换成数值常量。 问题起因源于:要对一个表达式进行分析,发现可能存在的错误,若无错误,则进行表达式运算;想要解决该问题...

    用自动状态变迁图方案从表达式中取出运算数

    问题:

    从键盘输入一个包含数字字符的字符串,从中取出符合双精度常量格式的数字字符串,并将其转换成数值常量。

    问题起因源于:要对一个表达式进行分析,发现可能存在的错误,若无错误,则进行表达式运算;想要解决该问题:首先得解决其中明显的技术性问题:括号匹配和从字符串中取数字字符串并转换成真正的数值常量。括号匹配在上一篇博文中已解决,在该篇中解决如何从字符串中取出符合双精度常量要求的字符串。

    思路:

    1.双精度常量由 正号、负号、小数点、数值组成。
    2.结合实际思考:如 34 3.4 -1.2 .3 3. 0. 都符合双精度常量格式;而 -. +. . 不符合双精度常量格式。
    3.双精度常量刚开始可以是:
    (1)符号: +,- ;(2)数值 (3)小数点 .
    如12.34.5 计算机能够正确取出12.34 和 .5 两个符合双精度格式的数值;但目前所编程序只能取出第一个正确的数值,12.34;

    了解了双精度常量格式后,给出一种高级方案:
    自动状态变迁图描述双精度常量格式且自动状态变迁图具有两种稳定状态: 开始状态 结束状态;

    得到自动状态变迁图如下:在这里插入图片描述

    根据自动状态变迁图编写代码如下:

    c代码:

    #include <stdio.h>
    #include <ctype.h>
    #include "glrError.h"
    
    #define NUMBER_START_STATUS 1
    #define NUMBER_INT_STATUS   2
    #define NUMBER_SIGN_STATUS  3
    #define NUMBER_DOT_STATUS   4
    #define NUMBER_DEC_STATUS   5
    #define NUMBER_END_STATUS   6
    
    typedef unsigned char boolean;
    #define TRUE 1
    #define FALSE 0
    
    typedef struct ARG{
    	int index;
    	int status;
    	boolean ok;
    	boolean finished;
    	double values;
    	int sign;
    	double dec;
    }ARG;	
    
    extern const char *errMess;
    
    boolean getNumber(const char *str,int *count,double *result);
    
    boolean isSign(int ch);
    void dealStartStatus(int ch,ARG *arg);
    void dealIntStatus(int ch,ARG *arg);
    void dealSignStatus(int ch,ARG *arg);
    void dealDotStatus(int ch,ARG *arg);
    void dealDecStatus(int ch,ARG *arg);
    
    void processInt(int ch,ARG *arg);
    void processSign(int ch,ARG *arg);
    void processDot(int ch,ARG *arg);
    void processDec(int ch,ARG *arg);
    
    void processDec(int ch,ARG *arg) {
    	arg->values += arg->dec * (ch - '0');
    	arg->dec/=10.0;
    }
    
    void processDot(int ch,ARG *arg) {
    	arg->dec = 0.1;
    }
    
    void processSign(int ch,ARG *arg) {
    	arg->sign = ('-' == ch ? -1 : 1);
    }
    
    void processInt(int ch,ARG *arg) {
    	arg->values = arg->values*10.0 + (ch - '0');
    }
    
    void dealDecStatus(int ch,ARG *arg) {
    	if(isdigit(ch)){
        		processDec(ch,arg);
          		arg->status = NUMBER_DEC_STATUS;
           		arg->index++; 
     	}else {
     		arg->status = NUMBER_END_STATUS;
     	}
    }
    
    void dealDotStatus(int ch,ARG *arg) {
    	if(isdigit(ch)){
      		processDec(ch,arg);
         		arg->status = NUMBER_DEC_STATUS;
         		arg->index++;	
    	}else {
    	 	errMess = "不能只出现小数点!\n";
    	 	arg->ok = FALSE;
    	}
    }
    
    void dealSignStatus(int ch,ARG *arg) {
    	if(isdigit(ch)){
    		processInt(ch,arg);
       		arg->status = NUMBER_INT_STATUS;
       		arg->index++;
    	}else if('.' == ch){
    		processDot(ch,arg);
      		arg->status = NUMBER_DOT_STATUS;
     		arg->index++;
    	}else {
    		errMess = "不可识别字符!\n";
    		arg->ok = FALSE;
    	}
    }
    
    void dealIntStatus(int ch,ARG *arg) {
    	if(isdigit(ch)){
    		processInt(ch,arg);
     		arg->status = NUMBER_INT_STATUS;
     		arg->index++;
    	}else if('.' == ch){
    		processDot(ch,arg);
    		arg->status = NUMBER_DEC_STATUS;
    		arg->index++;
    	}else {
    		arg->status = NUMBER_END_STATUS;
    	}
    }
    
    boolean isSign(int ch) {  
         return '+' == ch || '-' == ch;
    }
     
    
    void dealStartStatus(int ch,ARG *arg) {
    	if(isdigit(ch)){
    		processInt(ch,arg);
    		arg->status = NUMBER_INT_STATUS;
    		arg->index++;
    	}else if(isSign(ch)){
    		processSign(ch,arg);
    		arg->status = NUMBER_SIGN_STATUS;
    		arg->index++;
    	}else if('.' == ch){
    		processDot(ch,arg);
    		arg->status = NUMBER_DOT_STATUS;
    		arg->index++;
    	}else{
    		errMess = "出师未捷身先死!\n";
    		arg->ok = FALSE;
    	}
    }
    
    boolean getNumber(const char *str,int *count,double *result) {	
    	ARG arg = {
    	0,                         //index
    	NUMBER_START_STATUS,       //status
    	TRUE,                      //ok
    	FALSE,                     //finished
    	0.0,                       //values
    	1,                         //sign
    	0.0,                       //dec
    	};
    	
    	int ch;
    	
    	while(arg.ok && !arg.finished) {
    		ch = str[arg.index];
    		if(NUMBER_START_STATUS == arg.status){
    			dealStartStatus(ch,&arg);
    		}else if(NUMBER_INT_STATUS == arg.status){
    			dealIntStatus(ch,&arg);
    		}else if(NUMBER_SIGN_STATUS == arg.status){
    			dealSignStatus(ch,&arg);
    		}else if(NUMBER_DOT_STATUS == arg.status){
    			dealDotStatus(ch,&arg);
    		}else if(NUMBER_DEC_STATUS == arg.status){
    			dealDecStatus(ch,&arg);
    		}else if(NUMBER_END_STATUS == arg.status){
    		*count += arg.index;
    		*result = arg.values * arg.sign;
    		arg.finished = TRUE; 
    		}
    	}
    	return arg.ok;
    }
    
    int main(){
    
    	char str[80];
    	boolean ok;
    	int index = 0;
    	double values = 0.0;
    
    	printf("Input the str:");
    	gets(str);
    	
    	ok = getNumber(str,&index,&values);
    	if(ok) {
    	printf("%lf\n",values);
    	index++;
    	ok = getNumber(str+index,&index,&values);
    	if(ok){
    	printf("%lf\n",values);
    	}else{
    		showError();
    	}
    	}else{
    		showError();
    	}
    	
    	return 0;
    }			

    专门针对错误给出一套错误处理机制,这里需要glrError.h和glrError.c文件支持,代码如下:

    glrError.h文件:

    #ifndef _GLR_ERROR_H_
    #define _GLR_ERROR_H_
    
    void showError();
    
    #endif 

    glrError.c文件:

    #include <stdio.h>
    #include "glrError.h"
    
    const char *errMess = NULL;
    
    void showError(){
    	if(NULL == errMess) {
    	return;
    	}else{
    	printf("%s\n",errMess);
    	}
    }

    最后连编得到结果如下:

    结果:

    输入:-3.14+. 
    输出:-3.140000 
          不能只出现小数点!
    
    展开全文
  • 当然,每次成功问题转换成代码都小有激动,虽然只是黑框上输出了一些数字或是字符串。编程,虽然还不是很懂,但总感觉不只是学习知识这么简单,更多给我的感受是它潜移默化培养了人的一种能力,用自己的话来...

    经过一个学期的C语言学习,大体算是在这个编程语言上入了门,能够通过一些代码解决特定的问题。当然,每次成功将问题转换成代码都小有激动,虽然只是在黑框上输出了一些数字或是字符串。

    编程,虽然还不是很懂,但总感觉不只是学习知识这么简单,更多给我的感受是它在潜移默化中培养了人的一种能力,用自己的话来讲就是一种”代码能力“。对于同一个问题,让大家去解开答案,可能经过一些纸笔的运算都能得出结果,但是如何把这个问题转化成代码,这就是一种能力,而仅仅是将问题转换成代码,这是较为浅层次的能力,更深层的便是通过优化代码让程序运行时间缩短以及减少可能出现的bug。

    如果只是单纯的学习知识,像是背英语语法知识那样去学习一门编程语言、背下代码规则(当然熟识理论知识是必须的),这样可能也可以初步懂得这门语言,但是在深入上却较为困难。我始终觉得学习编程,重点在于培养写代码的能力。就拿写文章来说,对于文字的认识,可能大家都懂,但是给定一个题目,写出来的文章质量就各有差异,有的人文章平淡无奇,而有的人的却是宏篇大论。编程也是如此,懂得了理论知识,就像是认识了文字,但是优秀的作家能将这些文字巧妙地组合在一起形成佳作,优秀的程序员也是如此,能将大家都懂得的理论知识以一种更为巧妙的方法通过代码展示出来并使之可执行。

    所以,学习编程我始终认为我们每个人都应该注重写代码能力的培养。而这种培养可能需要无数次重复的练习,在获取这种能力的途中,可能有一部分人会觉得枯燥无味,因为始终看到的只是在黑色框框里输出一些数字以及字符串。刚开始的自己也是如此,但是后来那种解决问题的成就感慢慢克服了这种困难。给自己以有难度但又不超过自己能力范围的题目来练习,这样可能能逐步培养起兴趣。当然,因为每个人程度的不同,要找到适合自己能力范围的题目本身就是一种困难。以己之愚见,作为在校学生,老师的题目首先就是不错的选择,因为根据教学进度,老师都会给出不同的题目,而在此题目中必不乏难题存在,此时google一下,你可能就懂得了怎么去选择有难度又在自己能力范围的题目了。

    在这个学期里写过的程序大概有八十多个,包括老师的题目以及网上的oj练习,行数在三千行左右,当然因为是零基础进来的,所以在起步阶段,“水题”的部分占所写的程序总量应该不算少,因为相信扎实的基础可能对以后会大有裨益。虽然说是水题,但是在练习的过程也发现自身存在的很多问题,通过谷歌,一步步解决那种喜悦当然不必言说啦。编译器一直用的是Dev C++和Code:Blocks,中途也尝试过VS(作为新手总想试试鲜嘛),但是对于写C来说确实显得臃肿便放弃了。也试过几个编辑器,个人觉得atom和sublime的体验还是不错的,界面比较清爽,字体颜色较多能对不同部分代码加以区分。

    在今后的学习中希望能加强代码模块化的意识,可能现在提及模块化还显得偏早,但是意识总是早点树立会比较好。对于下学期要学习的面向对象的课程,总之加油吧。

    展开全文
  • C语言编程要点

    2017-09-18 00:10:37
    6.7. 怎样将数字转换字符串? 101 6.8. 怎样将字符串转换为数字? 103 6.9. 怎样打印字符串的一部分? 104 6.10. 怎样判断两个字符串是否相同? 105 第7章 指针和内存分配 106 7.1. 什么是间接引用(indirection)? 107 ...
  • *2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法? 2.6 为什么声明externf(structx*p);给我报了一个晦涩难懂的警告信息?  2.7 我遇到这样声明结构的代码:structname{intnamelen;charnamestr[1];}...
  • varchar2 1~4000字节 可变长度字符串,与CHAR类型相比,使用VARCHAR2可以节省磁盘空间,但查询效率没有char类型高 数值类型 Number(m,n) m(1~38) n(-84~127) 可以存储正数、负数、零、定点数和精度为38位的浮点数...
  • 你必须知道的495个C语言问题

    千次下载 热门讨论 2015-05-08 11:09:25
    *2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法? 2.6 为什么声明externf(structx*p);给我报了一个晦涩难懂的警告信息? 2.7 我遇到这样声明结构的代码:structname{intnamelen;charnamestr[1];}...
  • 编译原理 C语言实现词法分析

    热门讨论 2011-05-14 00:48:46
    词法分析,自文件头开始扫描源程序字符,一旦发现符合“单词”定义的源程序字符串时,它翻译固定长度的单词内部表示,并查填适当的信息表。 经过词法分析后,源程序字符串(源程序的外部表示)被翻译具有...
  •  在C语言中可从不同的角度对函数分类。 1. 从函数定义的角度看,函数可分为库函数和用户定义函数两种。 (1)库函数  由C系统提供,用户无须定义, 也不必在程序中作类型说明,只需在程序前包含有该函数原型的...
  • 《你必须知道的495个C语言问题》

    热门讨论 2010-03-20 16:41:18
    列出了C用户经常问的400多个经典问题,涵盖了初始化、数组、指针、字符串、内存分配、库函数、C预处理器等各个方面的主题,并分别给出了解答,而且结合代码示例阐明要点。 《你必须知道的495个C语言问题》结构...
  • *2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法? 22 2.6 为什么声明extern f(struct x *p); 给我报了一个晦涩难懂的警告信息? 23 2.7 我遇到这样声明结构的代码:struct name {int namelen; ...
  • 2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法? 2.6 为什么声明extern f(struct x *p); 给我报了一个晦涩难懂的警告信息? 2.7 我遇到这样声明结构的代码:struct name {int namelen; char namestr[1...
  • 难道在C语言中结构不能包含指向自己的指针吗? 1.15 如何定义一对相互引用的结构? 1.16 Struct{ }x1;和typedefstruct{ }x2;这两个声明有什么区别? 1.17 “typedefint(*funcptr)();”是什么意思? const...
  • 列出了C用户经常问的400多个经典问题,涵盖了初始化、数组、指针、字符串、内存分配、库函数、C预处理器等各个方面的主题,并分别给出了解答,而且结合代码示例阐明要点。 本书结构清晰,讲解透彻,是各高校相关...
  • 列出了C用户经常问的400多个经典问题,涵盖了初始化、数组、指针、字符串、内存分配、库函数、C预处理器等各个方面的主题,并分别给出了解答,而且结合代码示例阐明要点。  本书结构清晰,讲解透彻,是各高校...
  •  2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法?  2.6 为什么声明extern f(struct x *p); 给我报了一个晦涩难懂的警告信息?  2.7 我遇到这样声明结构的代码:struct name {int namelen; char ...
  • 2.5 在C语言中是否有模拟继承等面向对象程序设计特性的好方法? 2.6 为什么声明extern f(struct x *p); 给我报了一个晦涩难懂的警告信息? 2.7 我遇到这样声明结构的代码:struct name {int namelen; char namestr[1...
  • 注释命令,在C语言中相当与/*--------*/,它并不会被执行,只是起一个注释的作用,便于别人阅读和你自己日后修改。 Rem Message Sample:@Rem Here is the description. 5.Pause 命令 运行 Pause 命令时,显示...
  • 数据结构—栈的应用

    2017-06-15 11:37:25
    接着上次的栈的应用一,我们接着说说栈在计算机的一些具体应用。我们知道计算机的最初的本质工作就是做数学运算,...又如何在c语言中将中缀表达式转换成后缀表达式了? 解决方案: 遍历中缀表达式数字和符号

    接着上次的栈的应用一,我们接着说说栈在计算机中的一些具体应用。我们知道计算机的最初的本质工作就是做数学运算,那么计算机是如何读入字符串“9+(3-1)*5+8/2”并计算值的呢?

    在此我们就引入了后缀表达式这个新有概念:
    后缀表达式更符合计算机运算规则。
    那么后缀表达式又是怎样的呢?又如何在c语言中将中缀表达式转换成后缀表达式了?
    解决方案:
    遍历中缀表达式中的数字和符号
    对于数字:直接输出
    对于符号:
    左括号:进栈
    符号:与栈顶符号进行优先级比较
    若栈顶符号优先级低:进栈
    若栈顶符号优先级不低:将栈顶符号弹出并输出,之后进栈
    右括号:将栈顶符号弹出并输出,直到匹配到做括号
    遍历结束:将栈中的所有符号弹出并输出
    上面给出的解决方案就是中缀表达式转后缀表达式的具体方法.
    下面用几个例子来对此作以说明:
    实例: 5 + 3 => 5 3 +
    1+2*3=>123*+
    9+(3-1)5 =>931-5+
    那么,在C语言中实现的算法又是怎样的呢?
    中缀转后缀的算法框架
    当然,算法是建立在栈完成的基础上,栈又是基于线性表的。在之前也有贴出过栈与线性表的代码,有兴趣也可以在我的代码片里面查看。
    下面就是具体的中缀转后缀的代码

    #include <stdio.h>
    #include "LinkStack.h"
    
    int isNumber(char c)
    {
        return ('0' <= c) && (c <= '9');
    }
    
    int isOperator(char c)
    {
        return (c == '+') || (c == '-') || (c == '*') || (c == '/');
    }
    
    int isLeft(char c)
    {
        return (c == '(');
    }
    
    int isRight(char c)
    {
        return (c == ')');
    }
    
    int priority(char c)
    {
        int ret = 0;
    
        if( (c == '+') || (c == '-') )
        {
            ret = 1;
        }
    
        if( (c == '*') || (c == '/') )
        {
            ret = 2;
        }
    
        return ret;
    }
    
    void output(char c)
    {
        if( c != '\0' )
        {
            printf("%c", c);
        }
    }
    
    void transform(const char* exp)
    {
        LinkStack* stack = LinkStack_Create();
        int i = 0;
    
        while( exp[i] != '\0' )
        {
            if( isNumber(exp[i]) )
            {
                output(exp[i]);
            }
            else if( isOperator(exp[i]) )
            {
                while( priority(exp[i]) <= priority((char)(int)LinkStack_Top(stack)) )
                {
                    output((char)(int)LinkStack_Pop(stack));
                }
    
                LinkStack_Push(stack, (void*)(int)exp[i]);
            } 
            else if( isLeft(exp[i]) )
            {
                LinkStack_Push(stack, (void*)(int)exp[i]);
            } 
            else if( isRight(exp[i]) )
            {
                char c = '\0';
    
                while( !isLeft((char)(int)LinkStack_Top(stack)) )
                {
                    output((char)(int)LinkStack_Pop(stack));
                }
    
                LinkStack_Pop(stack);
            }
            else
            {
                printf("Invalid expression!");
                break;
            }
    
            i++;
        }
    
        while( (LinkStack_Size(stack) > 0) && (exp[i] == '\0') )
        {
            output((char)(int)LinkStack_Pop(stack));
        }
    
        LinkStack_Destroy(stack);
    }
    
    int main()
    {
        transform("9+(3-1)*5+8/2");
    
        printf("\n");
    
        return 0;
    }
    

    下来我们接着说后缀是如何在计算机中进行计算的?
    计算机对后缀表达式的运算时基于栈的,那么问题来了,在计算机中他是如何基于后缀表达式计算的呢?
    围绕这个问题,我们提出解决方案。
    解决方案:
    遍历后缀表达式中的数字和符号
    对于数字:进栈
    对于符号:
    从栈中弹出右操作数
    从栈中弹出左操作数
    根据符号进行运算
    将运算结果压入栈中
    遍历结束:栈中的唯一数字即为运算结果
    到这后缀表达式转换为计算机中的计算方式我想大家对此都有所了解了。
    下面来给出大家后缀运算的C语言算法框架。
    后缀运算算法框架
    具体实现代码如下:

    #include <stdio.h>
    #include "LinkStack.h"
    
    int isNumber(char c)
    {
        return ('0' <= c) && (c <= '9');
    }
    
    int isOperator(char c)
    {
        return (c == '+') || (c == '-') || (c == '*') || (c == '/');
    }
    
    int value(char c)
    {
        return (c - '0');
    }
    
    int express(int left, int right, char op)
    {
        int ret = 0;
    
        switch(op)
        {
            case '+':
                ret = left + right;
                break;
            case '-':
                ret = left - right;
                break;
            case '*':
                ret = left * right;
                break;
            case '/':
                ret = left / right;
                break;
            default:
                break;
        }
    
        return ret;
    }
    
    int compute(const char* exp)
    {
        LinkStack* stack = LinkStack_Create();
        int ret = 0;
        int i = 0;
    
        while( exp[i] != '\0' )
        {
            if( isNumber(exp[i]) )
            {
                LinkStack_Push(stack, (void*)value(exp[i]));
            }
            else if( isOperator(exp[i]) )
            {
                int right = (int)LinkStack_Pop(stack);
                int left = (int)LinkStack_Pop(stack);
                int result = express(left, right, exp[i]);
    
                LinkStack_Push(stack, (void*)result);
            }
            else
            {
                printf("Invalid expression!");
                break;
            }
    
            i++;
        }
    
        if( (LinkStack_Size(stack) == 1) && (exp[i] == '\0') )
        {
            ret = (int)LinkStack_Pop(stack);
        } 
        else 
        {
            printf("Invalid expression!");
        }
    
        LinkStack_Destroy(stack);
    
        return ret;
    }
    
    int main()
    {
        printf("9 + (3 - 1) * 5 + 8 / 2 = %d\n", compute("931-5*+82/+"));
    
        return 0;
    }

    小结:中缀表达式符合人类的阅读习惯
    后缀表达式是计算机喜欢的表达式
    通过栈可以方便的将中缀表达式变换为后缀表达式
    中缀表达式的计算过程类似程序编译运行的过程
    这篇博客是就到这了,需要强调的是,这篇是补充昨天的博客,今天的晚上会更新今天的博客。

    展开全文
  • 总结

    2019-01-04 17:41:08
    当然,每次成功问题转换成代码都小有激动,虽然只是黑框上输出了一些数字或是字符串。 编程,虽然还不是很懂,但总感觉不只是学习知识这么简单,更多给我的感受是它潜移默化培养了人的一种能力,用自己的话...
  • 21天学通C++ (中文第五版)

    热门讨论 2010-06-23 16:57:03
    3.1.1 数据存储内存 3.1.2 预留内存 3.1.3 整型变量的大小 3.1.4 基本变量类型 3.2 定义变量 3.2.1 区分大小写 3.2.2 命名规则 3.2.3 关键字 3.3 一次创建多个变量 3.4 给变量赋值 3.5 使用typedef...
  • 216 在字符串中查找一个子串 217 查找字符串中的标记 218 使用strtokf)解析一个字符串 219 扩展strtok函数以实现对空标记的解析 220 理解不区分大小写的函数 第二十二章 操作字符串 221 理解sizeof操作符 222 使用...
  • 216 在字符串中查找一个子串 217 查找字符串中的标记 218 使用strtokf)解析一个字符串 219 扩展strtok函数以实现对空标记的解析 220 理解不区分大小写的函数 第二十二章 操作字符串 221 理解sizeof操作符 222 使用...
  • 216 在字符串中查找一个子串 217 查找字符串中的标记 218 使用strtokf)解析一个字符串 219 扩展strtok函数以实现对空标记的解析 220 理解不区分大小写的函数 第二十二章 操作字符串 221 理解sizeof操作符 222 使用...
  • 216 在字符串中查找一个子串 217 查找字符串中的标记 218 使用strtokf)解析一个字符串 219 扩展strtok函数以实现对空标记的解析 220 理解不区分大小写的函数 第二十二章 操作字符串 221 理解sizeof操作符 222 使用...

空空如也

空空如也

1 2 3
收藏数 49
精华内容 19
关键字:

在c语言中如何将数字转换成字符串

c语言 订阅