【发布时间】:2013-06-25 21:57:55
【问题描述】:
对于不熟悉 MATLAB 的读者:不确定他们属于哪个家族,但 MATLAB 正则表达式已在here 进行了详细描述。 MATLAB 的注释字符是 %(百分比),它的字符串分隔符是 '(撇号)。字符串中的字符串定界符写为双撇号 ('this is how you write "it''s" in a string.')。更复杂的是,矩阵转置运算符也是撇号(A'(Hermitian)或A.'(常规))。
现在,出于黑暗的原因(我将不详细说明:),我正在尝试用 MATLAB 自己的语言解释 MATLAB 代码。
目前我正在尝试删除字符串单元格数组中的所有尾随 cmets,每个字符串都包含一行 MATLAB 代码。乍一看,这似乎很简单:
>> str = 'simpleCommand(); % simple trailing comment';
>> regexprep(str, '%.*$', '')
ans =
simpleCommand();
当然,可能会出现这样的情况:
>> str = ' fprintf(''%d%*c%3.0f\n'', value, args{:}); % Let''s do this! ';
>> regexprep(str, '%.*$', '')
ans =
fprintf(' %// <-- WRONG!
显然,我们需要从匹配中排除所有位于字符串中的注释字符,同时还要考虑到语句后面的单个撇号(或点撇号)是一个运算符 ,而不是字符串分隔符。
基于字符串打开/关闭字符的数量 before 注释字符必须是 even 的假设(我知道这是不完整的,因为矩阵转置运算符),我想出了以下动态正则表达式来处理这种情况:
>> str = {
'myFun( {''test'' ''%''}); % let''s '
'sprintf(str, ''%*8.0f%*s%c%3d\n''); % it''s '
'sprintf(str, ''%*8.0f%*s%c%3d\n''); % let''s '
'sprintf(str, ''%*8.0f%*s%c%3d\n''); '
'A = A.'';%tight trailing comment'
};
>>
>> C = regexprep(str, '(^.*)(?@mod(sum(\1==''''''''),2)==0;)(%.*$)', '$1')
然而,
C =
'myFun( {'test' '%'}); ' %// sucess
'sprintf(str, '%*8.0f%*s%c%3d\n'); ' %// sucess
'sprintf(str, '%*8.0f%*s%c%3d\n'); ' %// sucess
'sprintf(str, '%*8.0f%*s%c' %// FAIL
'A = A.';' %// success (although I'm not sure why)
所以我几乎在那里,但还没有:)
不幸的是,我已经用尽了我可以花在思考这个问题上的时间,需要继续做其他事情,所以也许其他有更多时间的人足够友好地思考这些问题:
- 字符串中的注释字符是我需要注意的唯一异常吗?
- 正确和/或更有效的方法是什么?
【问题讨论】:
-
我不知道 matlab 但如何使用非贪婪量词:
%.*?$ -
@M42:嗯,这似乎解决了这个问题,至少对于我的一小部分测试......你可以发布作为答案吗?
-
@M42: 等一下,我看的不够仔细——它没有解决问题……事实上,它不再做任何事情了:)
-
好吧,如果指令以分号结尾,可能会这样:用
;替换;\s*%.*?$ -
@M42:不幸的是,并非所有行都以分号结尾(例如,
if (condition) % trailing comment是一种常见的模式)
标签: regex string matlab parsing