在转换之前要先了解C的注释风格和C++的注释风格
-
C语言的注释风格:/* 注释内容 */
特点:可以注释多行 -
C++的注释风格:// 注释内容
特点:只能注释一行
那要将C注释转化为C++注释该怎么做呢?有多少种情况呢?我们画图来分析:
从文件中读取字符,我们就要考虑各种情况,以下:
input.c
// 1.一般情况
int num = 0;
/* int i = 0; */
// 2.换行问题
/* int i = 0; */int j = 0;
/* int i = 0; */
int j = 0;
// 3.匹配问题
/*int i = 0;/*xxxxx*/
// 4.多行注释问题
/*
int i=0;
int j = 0;
int k = 0;
*/int k = 0;
// 5.连续注释问题
/**//**/
// 6.连续的**/问题
/***/
// 7.C++注释问题
// /*xxxxxxxxxxxx*/
根据这七种情况,我们可以提取共同信息来分析,如图分析:
这样是不是就清晰的多了,下面看代码:
CommentConvert.h
#ifndef __COMMENT_CONVERT_H__
#define __COMMENT_CONVERT_H__
#include<stdio.h>
#include<stdlib.h>
typedef enum State
{
NUL_STATE,//无注释状态
C_STATE,//C注释状态
CPP_STATE,//C++注释状态
END_STATE//结束
}State;
void CommentConvert(FILE*pfRead, FILE*pfWrite);
void DoNulState(FILE*pfRead, FILE*pfWrite, State* ps);
void DoCState(FILE*pfRead, FILE*pfWrite, State* ps);
void DoCppState(FILE*pfRead, FILE*pfWrite, State* ps);
#endif//__COMMENT_CONVERT_H__
test.c
#define _CRT_SECURE_NO_WARNINGS 1
#include"CommentConvert.h"
void test()
{
FILE* pfRead = NULL;
FILE* pfWrite = NULL;
pfRead = fopen("input.c", "r");//从文件中读取字符
if (pfRead == NULL)
{
perror("open file for read");
exit(EXIT_FAILURE);
}
pfWrite = fopen("output.c","w");//向文件里写字符
if (pfWrite == NULL)
{
perror("open file for write");
exit(EXIT_FAILURE);
}
//注释转换
CommentConvert(pfRead, pfWrite);
fclose(pfRead);
pfRead = NULL;
fclose(pfWrite);
pfWrite = NULL;
}
int main()
{
test();
system("pause");
return 0;
}
CommentConvert.c
#define _CRT_SECURE_NO_WARNINGS 1
#include"CommentConvert.h"
void CommentConvert(FILE*pfRead, FILE*pfWrite)
{
//状态转换
State state = NUL_STATE;//初始化为无注释状态
while (state != END_STATE)
{
switch (state)
{
case NUL_STATE:
DoNulState(pfRead, pfWrite, &state);//无注释状态
break;
case C_STATE:
DoCState(pfRead, pfWrite, &state);//C状态
break;
case CPP_STATE:
DoCppState(pfRead, pfWrite, &state);//C++状态
break;
default:
break;
}
}
}
void DoNulState(FILE*pfRead, FILE*pfWrite, State* ps)
{
int first = fgetc(pfRead);
switch (first)
{
case '/':
{
int second = fgetc(pfRead);
switch (second)
{
case '*':
{
// /*表示进入C注释状态
fputc('/', pfWrite);
fputc('/', pfWrite);
*ps = C_STATE;
}
break;
case '/':
{
//两个//表示进入C++注释状态
fputc('/', pfWrite);
fputc('/', pfWrite);
*ps = CPP_STATE;
}
break;
default:
{
fputc('/', pfWrite);
fputc(second, pfWrite);
}
break;
}
}
break;
case EOF:
//EOF是文件结束标志
fputc(first, pfWrite);
*ps = END_STATE;
break;
default:
fputc(first, pfWrite);
break;
}
}
void DoCState(FILE*pfRead, FILE*pfWrite, State* ps)
{
int first = fgetc(pfRead);
switch (first)
{
case '*':
{
int second = fgetc(pfRead);
switch (second)
{
case '/':
{
//*/说明C注释结束,则进入无注释状态
*ps = NUL_STATE;
int third = fgetc(pfRead);
if (third == '\n')//判断是否有换行
{
fputc(third, pfWrite);
}
else
{
fputc('\n', pfWrite);
ungetc(third, pfRead);
//补充了换行符,所以读取的第三个字符要还回去,避免丢失
}
}
break;
default:
{
fputc(first, pfWrite);
ungetc(second, pfRead);
//一次打印一个字符,所以要还回去
}
break;
}
}
break;
case '\n':
{
//打印换行,在下一行打印//
fputc(first, pfWrite);
fputc('/', pfWrite);
fputc('/', pfWrite);
}
break;
default:
fputc(first, pfWrite);
break;
}
}
void DoCppState(FILE*pfRead, FILE*pfWrite, State* ps)
{
int first = fgetc(pfRead);
switch (first)
{
case '\n':
{
//说明C++状态结束,进入无注释状态
fputc('\n', pfWrite);
*ps = NUL_STATE;
}
break;
case EOF:
{
fputc(first, pfWrite);
*ps = END_STATE;
}
break;
default:
fputc(first, pfWrite);
break;
}
}
效果展示:
output.c
// 1.一般情况
int num = 0;
// int i = 0;
// 2.换行问题
// int i = 0;
int j = 0;
// int i = 0;
int j = 0;
// 3.匹配问题
//int i = 0;/*xxxxx
// 4.多行注释问题
//
//int i=0;
//int j = 0;
//int k = 0;
//
int k = 0;
// 5.连续注释问题
//
//
// 6.连续的**/问题
//*
// 7.C++注释问题
// /*xxxxxxxxxxxx*/
注意:
情况比较多要认真仔细的分析,一点一点的完成,尽力考虑到所有可能,我也是调试了好久才完成,不足之处,请多多指教!
版权声明:本文为dongying_原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。