Best of Ruby Quiz - MadLib

 题目大意明确,主要在于正则表达式运用

1]

首先是自己写的程序

 

str  =   % q {Our favorite language is ((gem:a gemstone)). We think ((gem)) is 
better than ((a gemstone)). }

hash 
=   {}

def read(prompt)
  print 
" Give Me #{prompt}: "
  gets.chomp  
end

while  str  =~   / \(\(. *? \)\) /
  pre,suc 
=  $`,$ '
  $ &   =~   / \(\((. *? )\:(. *? )\)\) | \(\((. *? )\)\) /
  key , prompt 
=  $ 1   ||  $ 3  , $ 2   ||  $ 3
  hash[key] 
||=  read(prompt)
  str 
=  pre  +  hash[key]  +  suc
end

print str + "\n"

属于比较正常的算法型想法,流式替换过程

 

2]

然后是书上的程序,最简短的那个

1 str  =   % q {Our favorite language is ((gem:a gemstone)). We think ((gem)) is 
2better than ((a gemstone)). }

3 hash  =  Hash. new   do   | hash,key |
4     print  " Give Me #{key.sub /\A([^:]+):/, ""  } : "
5     #p $ 1
6     hash[$ 1 =  gets.chomp
7 end
8 puts str.gsub( / \(\(([ ^ \)] + )\)\) / ) {hash[$1]}
9 #puts str.gsub( / \(\(([ ^ \)] + )\)\) /  , hash[$ 1 ])

 稍微有些出入,大体一样

做一些分析:

[0]这个程序存在BUG,如果把第五行注释解开,可以看到输出的第一个$1 = "gem" ,第二个$2 = "nil",BUG在后面我的改进里有修正

[1]第八行用gsub的Block形式十分重要,以下是Programming Ruby的节选

gsub 
带有block的形式,当前的匹配会作为参数传入block,并且会适当设置$1,$2,$`,$&,$'等变量

 如果用第9行的形式,会出现$1 = nil 的错误,因为用参数形式$1不能正确配置

 

 修正后的程序

1 str  =   % q {Our favorite language is ((gem:a gemstone)). We think ((gem)) is 
2better than ((a gemstone)). }

3 hash  =  Hash. new   do   | hash,key |
4     print  " Give Me #{key.sub /^([^:]+):/, ""  } : "
5     #p $ 1   ||  key
6     hash[$ 1   ||  key]  =  gets.chomp
7 end
8 puts str.gsub( / \(\(([ ^ \)] + )\)\) / ) {hash[$1]}

 

 修正的结果可以将注释行解开验证

你可能感兴趣的:(Ruby)