免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: send_linux
打印 上一主题 下一主题

正则表达进阶大讨论!欢迎参与讨论!(获奖名单已公布-2012-7-6) [复制链接]

论坛徽章:
0
91 [报告]
发表于 2012-06-15 16:23 |只看该作者
支持

论坛徽章:
0
92 [报告]
发表于 2012-06-17 01:08 |只看该作者
本帖最后由 kingbigeast 于 2012-06-17 01:11 编辑

学习正则表达式是从余晟翻译的《精通正则表达式》开始的,由于用vim的时发现很多时候都要用正则表达式。
从最基本的“锚点”、特殊符号,这些都是以前稍微明白一点的,而且不难上手。真正有意思的是在了解了诸如“匹配优先”,“忽略优先”,“固化分组”等等概念,还有不同引擎采用的不同思想:传统的NFA就是非确定有穷状态自动机,是表达式主导的,就是匹配的结果根据regex的增长而逐渐确定。而DFA是文本主导。每一次匹配,其实就是在文本空间做了一次搜索,不同的搜索策略的结果是一样的,就像BFS和DFS。由于NFA是表达式主导,所以表达式的质量直接关系到搜索效率。
【以上基本是我读书的心得。】
举一些我现在能想到的例子:

在调试代码的时候,会很频繁地添加和注释一些测试代码。在vim中,可以用一些键绑定特定的regex来实现:

  1. vmap <silent> <Leader>/ :s_^\(\s\)\?_\1//<CR>
  2. vmap <silent> <Leader>\ :s_^\(\s\)\?//_\1<CR>
复制代码
以上是C++里的注释和去注释,把斜杠换成#也可以在shell脚本中使用。
vim里的正则应该跟sed比较像,可能你注意到了,s替换的时候不是用/分隔的,而是下划线,这个特性我首先在sed中遇到,当模式中含有斜杠的时候特别有用。

*nux下很多工具的输出都是纯文本的,就是为了方便处理。而处理文本的工具必须要用正则表达式。
例如我想知道自己的IP,并把它赋给一个变量,首先用ifconfig得到包含本机IP的信息字符串,然后用grep找到感兴趣的行,最后用cut找到感兴趣的域:

  1. $ifconfig eth0 | grep "inet addr" | cut -d: -f2 | cut -d" " -f1
复制代码
当然这里并没用到什么高级的技巧。但有时候这个功能很需要,比如要用ffmpeg截取屏幕视频,要先知道窗口的坐标,xwininfo可以得到窗口信息,但要用grep或sed处理才能过滤出想要的结果。

再举一个Shell里用regex的例子。比如现在一直一个绝对路径,我要找到它的文件名和后缀名可以这样:

  1. $filepath=/home/bigeast/Desktop/try/te.c
  2. $filename=${filepath##*/}                #now $filename is te.c
  3. $filetype=${filename##.}                #now $filetype is c
  4. $file=${filename%*.c}                        #now $file is te
复制代码
两个#代表从做向右找最长的匹配(匹配优先),而一个%表示从右向左找最短的匹配(忽略优先)。

时间不早了,暂且写这么多,第一次上chinaunix,感觉氛围还不错。

论坛徽章:
1
技术图书徽章
日期:2014-04-24 15:46:21
93 [报告]
发表于 2012-06-17 10:06 |只看该作者
1、在你的日常工作中会使用正则表达式解决什么样的问题?
1 利用正则表达式解析用户输入的配置,或者配置文件里面的配置,
2 分析日志中的信息。
3 用户输入合法性的检测。比如用户输入一个IP,你必须检测用户输入的IP正确与否。

2、正则表达式的用法在各个语言、脚本里面略有不同,你有什么学习经验可以分享给初学者?
各种语言都有对正则表达式的支持,从我日常的C,Javascript,PHP, python,各种语言都支持正则表达式,
我们一向认为的不太适合解析字串的C也有对正则表达式的支持,但是C也有库来支持这个正则表达式。筒子们可以自行
百度regexec,js比较方便,有 RegExp 对象。

学习正则表达式,首先要理解正则表达式的规则,至于各种语言对正则表达式的支持,理解了正则表达式,自然也就水到渠成了。

论坛徽章:
49
15-16赛季CBA联赛之福建
日期:2016-06-22 16:22:002015年亚洲杯之中国
日期:2015-01-23 16:25:12丑牛
日期:2015-01-20 09:39:23未羊
日期:2015-01-14 23:55:57巳蛇
日期:2015-01-06 18:21:36双鱼座
日期:2015-01-02 22:04:33午马
日期:2014-11-25 09:58:35辰龙
日期:2014-11-18 10:40:07寅虎
日期:2014-11-13 22:47:15申猴
日期:2014-10-22 15:29:50摩羯座
日期:2014-08-27 10:49:43辰龙
日期:2014-08-21 10:47:58
94 [报告]
发表于 2012-06-17 12:12 |只看该作者
Bean_lee 发表于 2012-06-17 10:06
1、在你的日常工作中会使用正则表达式解决什么样的问题?
1 利用正则表达式解析用户输入的配置,或者配置文 ...


真是个潜水牛人啊,呵呵

论坛徽章:
2
午马
日期:2015-01-27 11:22:392015年辞旧岁徽章
日期:2015-03-03 16:54:15
95 [报告]
发表于 2012-06-18 11:02 |只看该作者
回复 101# kingbigeast


   
vim里的正则应该跟sed比较像,可能你注意到了,s替换的时候不是用/分隔的,而是下划线,这个特性我首先在sed中遇到,当模式中含有斜杠的时候特别有用。


  这边就是sed, sed的分隔符 其实可以用任意非特殊字符~~~比如abc~~

  后面这个字符串用'##'截取字符串的话, 应该是通配符"wildcard char",不算RE

论坛徽章:
0
96 [报告]
发表于 2012-06-18 16:02 |只看该作者
本帖最后由 kingbigeast 于 2012-06-18 16:03 编辑

回复 104# to407
  • 是可以是其它字符,我没想说全,比如“?”,“|”,“.”,但非特殊字符我不明白,它们都是特殊字符啊。
  • 我不是很清楚通配符和正则表达式的区别,正则表达式里不是也有通配符么。而且这里的最长匹配和最短匹配应该是正则表达式才有的概念吧。

写得太匆忙,领教了。

论坛徽章:
2
午马
日期:2015-01-27 11:22:392015年辞旧岁徽章
日期:2015-03-03 16:54:15
97 [报告]
发表于 2012-06-18 16:24 |只看该作者
回复 105# kingbigeast


    恩 第一点 我的意思是 任意可打印字符, 只要是所在命令行或者被包裹程序不需要转义的字符都可以拿来用, 甚至简单的 'a' 字符也行

    举个例子~~~

  1. -bash-3.00$ cat dbm.env
  2. export ORACLE_SID=orcl1

  3. -bash-3.00$ sed 'saORACLEaDATABASEag' dbm.env
  4. export DATABASE_SID=orcl1
复制代码

论坛徽章:
0
98 [报告]
发表于 2012-06-18 23:06 |只看该作者
回复 106# to407
哎,我看到特殊字符先想到的是在正则表达式里有特殊含义的字符而不是不可打印字符或者控制字符。。。

   

论坛徽章:
0
99 [报告]
发表于 2012-10-09 14:09 |只看该作者
都是高手.就我是菜鸟.
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP