[新手上路]批处理新手入门导读[视频教程]批处理基础视频教程[视频教程]VBS基础视频教程[批处理精品]批处理版照片整理器
[批处理精品]纯批处理备份&还原驱动[批处理精品]CMD命令50条不能说的秘密[在线下载]第三方命令行工具[在线帮助]VBScript / JScript 在线参考
返回列表 发帖

正则文本查找工具rf.exe

本帖最后由 happy886rr 于 2016-12-5 22:48 编辑

[2016/11/30]修复了ansi编码下/G:开关的漏洞,不作版本号提升,不作重新编译,只在核心源码中作了更新。

RF.EXE
-----------------------------------------------------------------------------
取代find、findstr的正则查找工具,智能识别文本编码,自动判断BOM类型。原生支持
ANSI、UTF8、Unicode、Unicode big endian编码。准确识别有无BOM类型。

支持pcre正则表达式查找、精确字符串查找,多种开关,完全模仿微软findstr的开关及
使用方法。具体用法与findstr大同小异,请自行品味。

源码完全开放,gcc、tcc均可编译。VC稍加修改亦能通过。
-----------------------------------------------------------------------------
COPYRIGHT@2016~2018 BY HAPPY, VERSION 1.0
REGEX FIND TOOLS
-----------------------------------------------------------------------------
rf [/F|/N|/V] [/S:[match string]     ]|
              [/R:[pcre expression]  ]|
              [/G:[ANSI strings file]] [txtfile]
-----------------------------------------------------------------------------
   /H  Show help information
   /F  Finds the line to which matches
   /N  Print the line number
   /V  Shows all rows that do not contain matching regulars
   /S: Finds the line to which the string matches
   /R: Finds the line to which the regular expression matches
   /G: Gets the matching strings from a ANSI strings file
-----------------------------------------------------------------------------
                                                                   11/06/2016

图片存为a.zip解压即是


核心代码:
  1. /*
  2. REGEX FIND TOOLS, VERSION 1.0
  3. RF.EXE
  4. COPYRIGHT@2016~2018 BY HAPPY
  5. */
  6. //静态编译(pcre)
  7. #define PCRE_STATIC
  8. #include    "pcre.h"
  9. #include   <stdio.h>
  10. #include  <string.h>
  11. #include  <locale.h>
  12. #include <stdbool.h>
  13. #include <windows.h>
  14. //定义行长(字节)
  15. #define BUFF_SIZE 4096
  16. //检测阈值(字节)
  17. #define CHECK_SIZE 16383
  18. //基础函数群
  19. char* UnicodeToANSI(const wchar_t* Str)
  20. {
  21. int L=WideCharToMultiByte(CP_ACP, 0, Str, -1, NULL, 0, NULL, NULL);
  22. char* Out=(char *)calloc(L+1, sizeof(char));
  23. WideCharToMultiByte(CP_ACP, 0, Str, -1, Out, L, NULL, NULL);
  24. return Out;
  25. }
  26. wchar_t* UTF8ToUnicode(const char* Str)
  27. {
  28. int L=MultiByteToWideChar(CP_UTF8, 0, Str,-1, NULL, 0);
  29. wchar_t* Out=(wchar_t *)calloc(L+1, sizeof(wchar_t));
  30. MultiByteToWideChar(CP_UTF8, 0, Str, -1, (LPWSTR)Out, L);
  31. return Out;
  32. }
  33. bool isUTF8(const char* Str)
  34. {
  35. if(!Str){
  36. return false;
  37. }
  38. const unsigned char* bytes=(const unsigned char *)Str;
  39. while(*bytes){
  40. if(
  41. (
  42. bytes[0]<=0x7F ||
  43. bytes[0]==0x09 ||
  44. bytes[0]==0x0A ||
  45. bytes[0]==0x0D ||
  46. (0x20<=bytes[0] && bytes[0]<=0x7E)
  47. )
  48. ){
  49. bytes+=1;
  50. continue;
  51. }
  52. if(
  53. (
  54. (0xC2<=bytes[0] && bytes[0]<=0xDF) &&
  55. (0x80<=bytes[1] && bytes[1]<=0xBF)
  56. )
  57. ){
  58. bytes+=2;
  59. continue;
  60. }
  61. if(
  62. (
  63.   (bytes[0]==0xE0) &&
  64. (0xA0<=bytes[1] && bytes[1]<=0xBF) &&
  65. (0x80<=bytes[2] && bytes[2]<=0xBF)
  66. ) ||
  67. (
  68. (
  69. (0xE1<=bytes[0] && bytes[0]<=0xEC)||
  70.                    bytes[0]==0xEE ||
  71.                    bytes[0]==0xEF
  72. ) &&
  73. (0x80<=bytes[1] && bytes[1]<=0xBF) &&
  74. (0x80<=bytes[2] && bytes[2]<=0xBF)
  75. ) ||
  76. (
  77.   (bytes[0]==0xED) &&
  78. (0x80<=bytes[1] && bytes[1]<=0x9F) &&
  79. (0x80<=bytes[2] && bytes[2]<=0xBF)
  80. )
  81. ){
  82. bytes+=3;
  83. continue;
  84. }
  85. if(
  86. (
  87.   (bytes[0]==0xF0) &&
  88. (0x90<=bytes[1] && bytes[1]<=0xBF) &&
  89. (0x80<=bytes[2] && bytes[2]<=0xBF) &&
  90. (0x80<=bytes[3] && bytes[3]<=0xBF)
  91. ) ||
  92. (
  93. (0xF1<=bytes[0] && bytes[0]<=0xF3) &&
  94. (0x80<=bytes[1] && bytes[1]<=0xBF) &&
  95. (0x80<=bytes[2] && bytes[2]<=0xBF) &&
  96. (0x80<=bytes[3] && bytes[3]<=0xBF)
  97. ) ||
  98. (
  99.   (bytes[0]==0xF4) &&
  100. (0x80<=bytes[1] && bytes[1]<=0x8F) &&
  101. (0x80<=bytes[2] && bytes[2]<=0xBF) &&
  102. (0x80<=bytes[3] && bytes[3]<=0xBF)
  103. )
  104. ){
  105. bytes+=4;
  106. continue;
  107. }
  108. return false;
  109. }
  110. return true;
  111. }
  112. //BOM检测
  113. int CheckBom(FILE* fp)
  114. {
  115. unsigned char* buf=(unsigned char*)calloc(3,sizeof(unsigned char));
  116. unsigned char* buf2;
  117. fseek(fp, 0, SEEK_SET);
  118. fread(buf, sizeof(unsigned char), 3, fp);
  119.      if(buf[0]==0xEF && buf[1]==0xBB && buf[2]==0xBF){return 3;}
  120. else if(buf[0]==0xFF && buf[1]==0xFE){return 5;}
  121. else if(buf[0]==0xFE && buf[1]==0xFF){return 6;}
  122. else{
  123. fseek(fp, 0, SEEK_SET);
  124. buf2=(unsigned char*)calloc(CHECK_SIZE,sizeof(unsigned char));
  125. fread(buf2, sizeof(unsigned char), CHECK_SIZE, fp);
  126. if(isUTF8(buf2)){
  127. free(buf2);
  128. return 2;
  129. }
  130. free(buf2);
  131. }
  132. return 1;
  133. }
  134. //正则查找函数
  135. int RFindLine(FILE* fp, char* src, int FLAG)
  136. {
  137. bool mode=false;
  138. int BOM=0, EN=0, i=0, n=0;
  139. FILE* sp;
  140. char* Li=(char *)malloc(BUFF_SIZE*sizeof(char));
  141. char* LineV;char* LineU;
  142. pcre  *re;
  143. int erroffset, ovector[30], rc;
  144. const char *error;
  145. if      ( (FLAG&0x0F)==0x02 ){
  146. pcre_compile(src, 0, &error, &erroffset, NULL);
  147. if( (re=pcre_compile(src, 0, &error, &erroffset, NULL)) == NULL ){
  148. fputs("PCRE compilation failed", stderr);
  149. exit(1);
  150. }
  151. }else if( (FLAG&0x0F)==0x03 ){
  152. if( (sp=fopen(src, "rb"))==NULL ){
  153. fputs("Read matching failed", stderr);
  154. exit(1);
  155. }
  156. }
  157. //BOM偏移值
  158. BOM=CheckBom(fp);
  159. if      (BOM==1 || BOM==2){
  160. EN=0;
  161. }else if(BOM==5 || BOM==6){
  162. EN=2;
  163. }else if(BOM==3){
  164. EN=3;
  165. }
  166. //执行偏移值
  167. fseek(fp, EN, SEEK_SET);
  168. //执行匹配过程
  169. if(BOM==1){
  170. char* Line=(char *)malloc(BUFF_SIZE*sizeof(char));
  171. while(!feof(fp)){
  172. memset(Line, 0, BUFF_SIZE*sizeof(char));
  173. fgets(Line, BUFF_SIZE, fp);
  174. i++;
  175. if      ( (FLAG&0x0F)==0x01 ){
  176. if( strstr(Line, src)!=NULL ){
  177. mode=true;
  178. }else{
  179. mode=false;
  180. }
  181. }else if( (FLAG&0x0F)==0x02 ){
  182. if( pcre_exec(re, NULL, Line, strlen(Line), 0, 0, ovector, 30) >= 0 ){
  183. mode=true;
  184. }else{
  185. mode=false;
  186. }
  187. }else if( (FLAG&0x0F)==0x03 ){
  188. mode=false;
  189. fseek(sp, 0, SEEK_SET);
  190. while(!feof(sp)){
  191. memset(Li, 0, BUFF_SIZE*sizeof(char));
  192. fgets(Li, BUFF_SIZE, sp);
  193. char* tp=Li;
  194. while(*tp=='\t' ||*tp==' ' ||*tp=='\r' ||*tp=='\n'){tp++;}
  195. int tp_LEN=strlen(tp);
  196. tp[tp_LEN-2]=(tp[tp_LEN-2]=='\r')?'\0':tp[tp_LEN-2];
  197. if(tp[0]!='\0' &&strstr(Line, tp)!=NULL){
  198. mode=true;
  199. break;
  200. }
  201. }
  202. }
  203. //输出显示
  204. if( (FLAG>>4)==0x03 && mode==true ){
  205. fprintf(stdout, "%d:%s", i, Line);
  206. }else if(
  207. ((FLAG>>4)==0x02 && mode==false)||
  208. ((FLAG>>4)==0x01 && mode==true )
  209. ){
  210. fputs(Line, stdout);
  211. }
  212. }
  213. }else if(BOM==2 || BOM==3){
  214. char* Line=(char *)malloc(BUFF_SIZE*sizeof(char));
  215. while(!feof(fp)){
  216. memset(Line, 0, BUFF_SIZE*sizeof(char));
  217. fgets(Line, BUFF_SIZE, fp);
  218. i++;
  219. if(BOM>1){LineU=UnicodeToANSI(UTF8ToUnicode(Line));}
  220. if      ( (FLAG&0x0F)==0x01 ){
  221. if( strstr(LineU, src)!=NULL ){
  222. mode=true;
  223. }else{
  224. mode=false;
  225. }
  226. }else if( (FLAG&0x0F)==0x02 ){
  227. if( pcre_exec(re, NULL, LineU, strlen(LineU), 0, 0, ovector, 30) >= 0 ){
  228. mode=true;
  229. }else{
  230. mode=false;
  231. }
  232. }else if( (FLAG&0x0F)==0x03 ){
  233. fseek(sp, 0, SEEK_SET);
  234. while(!feof(sp)){
  235. memset(Li, 0, BUFF_SIZE*sizeof(char));
  236. fgets(Li, BUFF_SIZE, sp);
  237. if( strstr(LineU, Li)!=NULL ){
  238. mode=true;
  239. break;
  240. }
  241. }
  242. }
  243. //输出显示
  244. if( (FLAG>>4)==0x03 && mode==true ){
  245. fprintf(stdout, "%d:%s", i, LineU);
  246. }else if(
  247. ((FLAG>>4)==0x02 && mode==false)||
  248. ((FLAG>>4)==0x01 && mode==true )
  249. ){
  250. fputs(LineU, stdout);
  251. }
  252. }
  253. }else if(BOM==5){               //Unicode
  254. wchar_t* LineW=(wchar_t *)calloc(BUFF_SIZE, sizeof(wchar_t));
  255. while(!feof(fp)){
  256. memset(LineW, 0, BUFF_SIZE*sizeof(wchar_t));
  257. fgetws(LineW, BUFF_SIZE, fp);
  258. i++;
  259. LineV=UnicodeToANSI(LineW);
  260. if      ( (FLAG&0x0F)==0x01 ){
  261. if( strstr(LineV, src)!=NULL ){
  262. mode=true;
  263. }else{
  264. mode=false;
  265. }
  266. }else if( (FLAG&0x0F)==0x02 ){
  267. if( pcre_exec(re, NULL, LineV, strlen(LineV), 0, 0, ovector, 30) >= 0 ){
  268. mode=true;
  269. }else{
  270. mode=false;
  271. }
  272. }else if( (FLAG&0x0F)==0x03 ){
  273. fseek(sp, 0, SEEK_SET);
  274. while(!feof(sp)){
  275. memset(Li, 0, BUFF_SIZE*sizeof(char));
  276. fgets(Li, BUFF_SIZE, sp);
  277. if( strstr(LineV, Li)!=NULL ){
  278. mode=true;
  279. break;
  280. }
  281. }
  282. }
  283. if      ( (FLAG>>4)==0x03 && mode==true ){
  284. fprintf(stdout, "%d:%s", i, LineV);
  285. }else if(
  286. ((FLAG>>4)==0x02 && mode==false)||
  287. ((FLAG>>4)==0x01 && mode==true )
  288. ){
  289. fputs(LineV, stdout);
  290. }
  291. }
  292. }else if(BOM==6){               //Unicode big endian
  293. wchar_t* LineW=(wchar_t *)calloc(BUFF_SIZE, sizeof(wchar_t));
  294. while(!feof(fp)){
  295. memset(LineW, 0, BUFF_SIZE*sizeof(wchar_t));
  296. fgets(LineW, BUFF_SIZE, fp);
  297. i++;
  298. for(n=0;LineW[n]!=0x0000;n++){
  299. LineW[n]=(LineW[n]&0x00FF)<<8|(LineW[n]&0xFF00)>>8;
  300. }
  301. LineV=UnicodeToANSI(LineW);
  302. if      ( (FLAG&0x0F)==0x01 ){
  303. if( strstr(LineV, src)!=NULL ){
  304. mode=true;
  305. }else{
  306. mode=false;
  307. }
  308. }else if( (FLAG&0x0F)==0x02 ){
  309. if( pcre_exec(re, NULL, LineV, strlen(LineV), 0, 0, ovector, 30) >= 0 ){
  310. mode=true;
  311. }else{
  312. mode=false;
  313. }
  314. }else if( (FLAG&0x0F)==0x03 ){
  315. fseek(sp, 0, SEEK_SET);
  316. while(!feof(sp)){
  317. memset(Li, 0, BUFF_SIZE*sizeof(char));
  318. fgets(Li, BUFF_SIZE, sp);
  319. if( strstr(LineV, Li)!=NULL ){
  320. mode=true;
  321. break;
  322. }
  323. }
  324. }
  325. if      ( (FLAG>>4)==0x03 && mode==true ){
  326. fprintf(stdout, "%d:%s", i, LineV);
  327. }else if(
  328. ((FLAG>>4)==0x02 && mode==false)||
  329. ((FLAG>>4)==0x01 && mode==true )
  330. ){
  331. fputs(LineV, stdout);
  332. }
  333. }
  334. }
  335. fflush(stdout);
  336. if( (FLAG&0x0F)==0x02 ){pcre_free(re);}
  337. free(Li);
  338. return 0;
  339. }
  340. //帮助信息
  341. void Help_Info(FILE* stream, int Exit_Code)
  342. {
  343. fprintf(stream,
  344. "COPYRIGHT@2016~2018 BY HAPPY, VERSION 1.0\n"
  345. "REGEX FIND TOOLS\n"
  346. "-----------------------------------------------------------------------------\n"
  347. "rf [/F|/N|/V] [/S:[match string]     ]|\n"
  348. "              [/R:[pcre expression]  ]|\n"
  349. "              [/G:[ANSI strings file]] [txtfile]\n"
  350. "-----------------------------------------------------------------------------\n"
  351. "   /H  Show help information\n"
  352. "   /F  Finds the line to which matches\n"
  353. "   /N  Print the line number\n"
  354. "   /V  Shows all rows that do not contain matching regulars\n"
  355. "   /S: Finds the line to which the string matches\n"
  356. "   /R: Finds the line to which the regular expression matches\n"
  357. "   /G: Gets the matching strings from a ANSI strings file\n"
  358. "-----------------------------------------------------------------------------\n"
  359. "                                                                   11/06/2016\n"
  360. );
  361. exit(Exit_Code);
  362. }
  363. //主函数入口
  364. int main(int argc, char** argv)
  365. {
  366. FILE* fp;
  367. unsigned char FLAG=0;
  368. if( (argc==4) && (argv[1][0]=='/') && (argv[2][0]=='/') && (argv[2][2]== ':') ){
  369. switch(argv[1][1]){
  370. case 'F':
  371. case 'f':
  372. FLAG|=0x10;
  373. break;
  374. case 'V':
  375. case 'v':
  376. FLAG|=0x20;
  377. break;
  378. case 'N':
  379. case 'n':
  380. FLAG|=0x30;
  381. break;
  382. default:
  383. Help_Info(stderr, 2);
  384. }
  385. switch(argv[2][1]){
  386. case 'S':
  387. case 's':
  388. FLAG|=0x01;
  389. break;
  390. case 'R':
  391. case 'r':
  392. FLAG|=0x02;
  393. break;
  394. case 'G':
  395. case 'g':
  396. FLAG|=0x03;
  397. break;
  398. default:
  399. Help_Info(stderr, 1);
  400. }
  401. }else {
  402. Help_Info(stderr, 3);
  403. }
  404. if( (fp=fopen(argv[3], "rb"))==NULL ){
  405. fputs("Read failed", stderr);
  406. return 3;
  407. }
  408. RFindLine(fp, argv[2]+3, FLAG);
  409. fclose(fp);
  410. return 0;
  411. }
复制代码
1

评分人数

又在重复造轮子, 缩进不要超过3层

TOP

回复 2# Bella


    别人的造的轮子是别人的。自己造的轮子才是自己的。
去学去写去用才有进步。安装python3代码存为xx.py 双击运行或右键用IDLE打开按F5运行

TOP

求教,如何把字符串 “D:\My Documents\Pictures\★★★2016113-154wer52.jpg" 中的文件名用正则表达式提取出来?

我想得到的字符串是这个 “★★2016113-154wer52.jpg”  (注意:文件名少一个 ★ 号)。

正则测试工具用  (?<=★).*  是行的。但不知RF怎么写。

TOP

好东西好东西好东西

TOP

回复 4# sanmaodo
容易,在rf源码的227行下面添加如下代码。编译成exe即可提取子串。
  1. for (int i = 0; i < pcre_exec(re, NULL, Line, strlen(Line), 0, 0, ovector, 30); i++) {
  2.         char *getkeywords = src + ovector[2*i];
  3.         printf("%s\n",getkeywords);
  4. }
复制代码
rf使用pcre正则,因此,你的正则式  (?<=★).*无需更改,直接使用。
rf暂时不开放其他特殊功能,这个模块请自行添加用gcc或tcc编译即可。
1

评分人数

TOP

回复 6# happy886rr
非常感谢!

TOP

gcc需要在linux中编译,还是可以在windows的gcc就可以?

TOP

回复 8# freesoft00
那个图片存为zip格式,必须用winrar软件才能解压,压缩包里有exe文件,不用编译,要编译也只支持windows下的gcc编译。

TOP

回复 9# happy886rr


    压缩包里有exe文件

exe不是最新版本呀。

TOP

本帖最后由 523066680 于 2016-12-1 15:25 编辑

回复 10# freesoft00


有这一句   #include <windows.h>
当然是 windows

话说没去试就问问题也是服了 。。。

我觉得楼主可以开一个网盘专门分享附件。图片另存-改扩展名-解压 其实也不太方便。

TOP

回复 11# 523066680
很好的建议,我之前的好多图片都是外链,那些图片网站只保存半个月,就让我的图片失效了。下回直接整百度网盘吧。

TOP

回复 10# freesoft00
也对,编译参数是
  1. gcc RF.c -lpcre -L./ -oRF.exe
复制代码
windows下最好用mingw32编译器。使用-O3优化以达到最佳编译效果。后续我将会去开发linux的第三方,之后的第三方我将尽量提供双平台版本以及安卓手机版。
1

评分人数

TOP

回复 13# happy886rr

https://sourceforge.net/projects/mingw/files/?source=navbar
https://sourceforge.net/projects/mingw-w64/files/?source=navbar
这两个是哪一个。不好意思,对这个不熟悉,所以问的问题比较初级。

TOP

本帖最后由 523066680 于 2016-12-1 19:03 编辑

回复 14# freesoft00


    https://nuwen.net/mingw.html

二选一
mingw-14.0.exe
mingw-14.0-without-git.exe
1

评分人数

TOP

返回列表