c语言版去除源代码注释
- 去除代码中注释需要注意下面几点 
首先注释有”/*”开始到”*/”结束的多行或单行注释
其次还有”//”这种单行注释
另外还需要注意双引号和单引号内的字符不要算到注释中 - 因此我设计以下程序 
当遇到””“双引号和”’“时需要跳过整个字符串,特别注意字符串和字符内部转义字符。
当遇到”/“斜杠时,匹配下一个为星号还是斜杠,如果下一个是斜杠则直接跳到本行结尾。如果是星号则匹配”*/” - 下面是源代码,没啥特别的
 
#include <stdio.h>
#include <ctype.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/stat.h>
/**
* 去掉字符串中注释部分
**/
void remove_comment(char *buf)
{
  size_t off;
  char *s, *p, *t, *tmp;
  char *sss="adas\"d/**/\"*a\"//s/**/d*/"; // 这里主要测试字符串内带注释字符
  for (s = p = buf; *p != '\0'; p++) {
    switch(*p) {
      case '"': // 直接循环到下一个 "
      case '\'': /* 直接循环到下一个 ' */
          // 下面找到字符串结束位置,避免匹配字符串内部的 /* 或者 //
        for (tmp = p + 1; *tmp != *p; tmp++) {
          if (*tmp == '\\') {
            tmp++; /* 跳过转义位置,因为转义字符2个位置代表一个字符 */
          }
        }//阿萨德撒
        // while(1) {
          // if ( NULL != (t = strchr(tmp, '\\')) ) {
        // printf("%c\n", *tmp);
            // tmp = t + 2; // 有转义字符
          // }
          // if ( NULL != (t = strchr(tmp, *p)) ) {
            // tmp = t + 1; // 有要找的字符
            // break;
          // }
        // }
        // printf("%c\n", *(tmp-2));
        // exit(0);
        // while ( NULL != (t = strchr(tmp, *p)) ) {
          // tmp = t + 1; /*每次都从下一个位置找*/
          // if ( *(t - 1) != '\\' ) {
            // break; // 这次的符号不是转义,则表示找到真正字符串末尾了
          // }
        // }
        off = tmp - p+1/* 计算本次拷贝长度 */;
        if (off > 1) {
          strncpy(s, p, off);
          p += off - 1; // 外面有一个p++,所以这里少加一个
          s += off;
        }
      break;
      case '/':
        switch ( *(p + 1) ) {
          case '*': // 组成 /*
            if (NULL != (t = strstr(p + 1, "*/"))) {
              p = t + 1; /* 这里把指针指向 /* 结束标记 */
            }
          break;
          case '/':  //  组成 //
            for (tmp = p - 1; 0 != isspace(*tmp); tmp--) {
            } // /* 这里的循环用于去掉空行注释
            s -= p - tmp - 1; // s倒退到上一个非空白字符
            *s++ = '\n'; /* //是单行注释,因此必须有一个换行 */
            while (*p != '\n' && *p != '\r') {
              p++;//  p指针移到下一个回车换行
            }
          break;
          default: // 没有匹配注释字符
            *s++ = *p;
          break;
        }
      break;
      default: // 没有匹配字符则逐个写
        *s++ = *p;
      break;
    }
  }
  *s = '\0'; // 写结束标记
}
/**
* 因为一个源码文件最大也就几M
* 所以全部读到内存处理,绰绰有余的
* 这里是多行注释,去掉后会有一个回车
* 及多行注释缩短为一行
**/
int main(int argc, char *argv[])
{
  if (argc != 2) { /* 传递参数不正确 */
    printf("Usage : %s file.c\n", argv[0]);
    return -1;
  }
  const char *filename = argv[1]; // 得到文件名
  struct stat statbuff;  /* 得到文件信息结构体 */
  if(stat(filename, &statbuff) < 0){
    return -1; // 获取文件大小失败
  }
  off_t filesize = statbuff.st_size; // 缓存文件大小
  char *fileBuff = (char *)malloc(sizeof(char) * filesize);
  int fd = open(filename, O_RDONLY);
  if (-1 == fd) {
    printf("open %s : %s\n", filename, strerror(errno));
    return errno;
  }
  ssize_t n = read(fd, fileBuff, filesize);
  if (n <= 0) { // 读取错误或空文件,直接关闭文件并退出
    close(fd);
    return -1;
  }
  *(fileBuff + n) = '\0'; /* 加上结束符 */
  remove_comment(/* 直接把参数分成2半咯 */fileBuff); // 去除注释
  printf("%s\n", fileBuff); /* 打印结果 */
  close(fd);
  return 0;
}
4.下面演示一下功能,将上面的文件保存为main.c,执行 
 gcc main.c && .\a.exe main.c
#include <stdio.h>
#include <ctype.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/stat.h>
void remove_comment(char *buf)
{
  size_t off;
  char *s, *p, *t, *tmp;
  char *sss="adas\"d/**/\"*a\"//s/**/d*/";
  for (s = p = buf; *p != '\0'; p++) {
    switch(*p) {
      case '"':
      case '\'':
        for (tmp = p + 1; *tmp != *p; tmp++) {
          if (*tmp == '\\') {
            tmp++;
          }
        }
        off = tmp - p+1;
        if (off > 1) {
          strncpy(s, p, off);
          p += off - 1;
          s += off;
        }
      break;
      case '/':
        switch ( *(p + 1) ) {
          case '*':
            if (NULL != (t = strstr(p + 1, "*/"))) {
              p = t + 1;
            }
          break;
          case '/':
            for (tmp = p - 1; 0 != isspace(*tmp); tmp--) {
            }
            s -= p - tmp - 1;
            *s++ = '\n';
            while (*p != '\n' && *p != '\r') {
              p++;
            }
          break;
          default:
            *s++ = *p;
          break;
        }
      break;
      default:
        *s++ = *p;
      break;
    }
  }
  *s = '\0';
}
int main(int argc, char *argv[])
{
  if (argc != 2) {
    printf("Usage : %s file.c\n", argv[0]);
    return -1;
  }
  const char *filename = argv[1];
  struct stat statbuff;
  if(stat(filename, &statbuff) < 0){
    return -1;
  }
  off_t filesize = statbuff.st_size;
  char *fileBuff = (char *)malloc(sizeof(char) * filesize);
  int fd = open(filename, O_RDONLY);
  if (-1 == fd) {
    printf("open %s : %s\n", filename, strerror(errno));
    return errno;
  }
  ssize_t n = read(fd, fileBuff, filesize);
  if (n <= 0) {
    close(fd);
    return -1;
  }
  *(fileBuff + n) = '\0';
  remove_comment(fileBuff);
  printf("%s\n", fileBuff);
  close(fd);
  return 0;
}												
											c语言版去除源代码注释的更多相关文章
- Microsoft源代码注释语言(SAL)提供设置批注
		
Microsoft源代码注释语言(SAL)提供设置批注可以使用描述的功能如何使用其参数,它对其假设并确保它使其在完成. 批注可标头文件 <sal.h>定义. Visual Studio C ...
 - DevOps:怎么实现源代码注释和系统文档的自动化更新?
		
[编者按]计算机软件传统定义为:软件是计算机系统中与硬件相依存的另一部分,软件包括程序.数据及其相关文档的完整集合.然而在时下的开发中,文档的合规性往往被忽视的干干净净.本文由 Todd Waits ...
 - 基于gSOAP使用头文件的C语言版web service开发过程例子
		
基于gSOAP使用头文件的C语言版web service开发过程例子 一服务端 1 打开VS2005,创建一个工程,命名为calcServer. 2 添加一个头文件calc.h,编辑内容如下: 1// ...
 - CentOS-6.4-minimal版中源代码安装MySQL-5.5.38
		
完整版见https://jadyer.github.io/2014/09/29/centos-install-mysql/ /** * CentOS-6.4-minimal版中源代码安装MySQL-5 ...
 - 基于BP神经网络的简单字符识别算法自小结(C语言版)
		
本文均属自己阅读源代码的点滴总结.转账请注明出处谢谢. 欢迎和大家交流.qq:1037701636 email:gzzaigcn2009@163.com 写在前面的闲话: 自我感觉自己应该不是一个非常 ...
 - c++学习书籍推荐《清华大学计算机系列教材:数据结构(C++语言版)(第3版)》下载
		
百度云及其他网盘下载地址:点我 编辑推荐 <清华大学计算机系列教材:数据结构(C++语言版)(第3版)>习题解析涵盖验证型.拓展型.反思型.实践型和研究型习题,总计290余道大题.525道 ...
 - GeoIP的使用-C语言版
		
0x00. 简介 GeoIP库可以根据IP地址(支持IPv4 和 IPv6), 定位该IP所在的 洲.经纬度.国家.省市.ASN 等信息. GeoIP目前已经升级到GeoIP2,GeoIP2有两个版本 ...
 - libnode 0.4.0 发布,C++ 语言版的 Node.js
		
libnode 0.4.0 支持 Windows ,提升了性能,libuv 更新到 0.10.17 版本,libj 更新到 0.8.2 版本. libnode 是 C++ 语言版的 Node.js,和 ...
 - md5加密算法c语言版
		
from: http://blog.sina.com.cn/s/blog_693de6100101kcu6.html 注:以下是md5加密算法c语言版(16/32位) ---------------- ...
 
随机推荐
- 在遍历ResultSet的循环中再执行SQL会发生什么(前提:同一个Statement)
			
如下面代码: Class.forName(DBParam.Driver).newInstance(); conn = DriverManager.getConnection(DBParam.DbUrl ...
 - 使用wangEditor富文本编辑器
			
客户端配置说明 下载 百度网盘地址:点我下载 下载密码:x09x 使用 首先要引入wangEditor的js文件,然后引入jQuery 然后在body里: <body> <butto ...
 - 借助Java的JDBC自制“DBMS”管理操作数据库
			
package jdbc; import java.sql.Connection; import java.sql.Driver; import java.sql.DriverManager; imp ...
 - 如何把Github上好的项目pull到本地或者fork到本地(码云仓库同理)?
			
首先Github账户的注册我就不想再啰嗦了,我想大家都会的. 其次怎么把自己的项目push到自己的Github仓库请参考我的另一篇博客: 如何把自己开发的项目上传到GitHub仓库或者码云仓库? 最后 ...
 - linux定时重启服务器
			
需求说明 系统配置低了,且应用程序内一直在执行定时任务,在程序运行一段时间后,发现接口请求会变得很慢,需要每天定时凌晨重启服务器 脚本实现 1. linux 终端输入crontab -e,添加定时任务 ...
 - FFmpeg开发笔记(五):ffmpeg解码的基本流程详解(ffmpeg3新解码api)
			
若该文为原创文章,未经允许不得转载原博主博客地址:https://blog.csdn.net/qq21497936原博主博客导航:https://blog.csdn.net/qq21497936/ar ...
 - Python实现自动生成小学四则运算题目
			
Github地址: https://github.com/guoyuyi/gyy.github.io/blob/%E4%BD%9C%E4%B8%9A1/zy1.py 题目描述: 通过python语言编 ...
 - CVE-2018-8045
			
Joomla!Core SQL注入漏洞 CVE-2018-8045 受影响版本:joomla!3.5.0-3.8.5 漏洞描述: joomla!3.5.0-3.8.5版本对sql语句内的变量缺少类型转 ...
 - 自定义带边框TextView--边框粗细不一的问题
			
自定义带边框TextView 给textview加边框 最low的做法.textview外层套一层布局,然后给布局加边框样式(这么弱的做法,不能这么干) 自定义控件 canvas.drawLines ...
 - 一次性升级所有python包的靠谱并且简单的方法
			
1. 用pip-review包pip install pip-review #安装包pip-review --auto #自动批量升级指令2. 编写代码import pipfro ...