问题来源
在linux,为了使用方便难免要把自己的程序的目录放到环境变量中(通过修改home目录下.profile ,.bash_pro, .bashrc 这种文件实现),在用kaldi的时候我也是这样。假设这个程序是 your_exe ,那么就可以在shell中像输入 mv,echo,ls等一样使用。
我们知道在ruby中调用一个shell命令可以使用 ``,system,%x[],exec等。 我们可以写类似的命令
`ll | awk '{print $0}' | echo `
这样是没问题的,然而我发现一个有趣的现象,它令我当天花费2h解决,但是无果,让我伤心至极
` your_exe ` 这样your_exe可以运行 至今我解释不了为什么这个可以运行
`cat file | egrep -v 'exp' | your_exe ` 居然提示your_exe找不到
(%x[] 与 ``作用类似,不过可以写多行)
解决之路
首先原因估计是是环境变量没有加载进来,但我的疑惑处在上面写出了。
1.考虑ruby运行时的环境 (错误思路)
我以为%x[] 这种调用方式使用的环境变量是ruby运行的环境变量,于是使用下面的方法
path="#{kaldipath}/src/bin/"
$LOAD_PATH.unshift path
p $LOAD_PATH
结果还是找不到
后来我明白原来调用系统命令的方式是另起进程,所以环境变量可能会改变。(只是猜测)
2.在%x[]中先加入环境变量
首先我这样做
%x[
source ~/.profile
]
说是找不到source,联想起我之前探索的cd这个命令的问题,才知道cd,source,以及. (点) 这三个为系统级别的命令,根本没有实在的程序,shell遇到它们会做特殊的处理,一般只有sh脚本才能直接用。
在我感觉失望之余,我想到可以使用export PATH=$PATH:add_path,结果成功了。
3.优化
我想既然export可以不就可以直接把 .profile中的内容直接当成命令吗,于是就如下写
a=File.open("~/.profile").read
%x[
#{a}
(test cmd line)
]
结果发现ruby不认识~符号,改了之后发现还是不行。这个错误找了很久最后我才发现原来那个文件里面有~这个符号,因此就只好设法替换大致如下
home_path=`echo -n ~`
......
a.gsub!(/~/,home_path)
最后总算可以了。
总结
任何事情都是熟能生巧吧,每个语言都有自己的问题,只有用的多了才知道,所以希望自己不要再被语言之争而弄的心烦意乱,学好(但不要刻意学)一个语言就可以了,毕竟语言不算什么。有些东西的确需要对系统有所了解才能少犯错误,或者犯了错误也能较快察觉。