2016-01-28 28 views
1

背景如何从脚本运行ispell时了解并避免非交互式模式错误?

的ispell是在linux基本命令行的拼写程序,我想呼吁的文件名以前收集的名单。例如,这些文件名是从乳胶根文件递归收集的。当需要拼写所有递归包含的latex文件时,这是有用的,并且不需要其他文件。然而,从命令行调用ispell事实证明是不平凡的,因为ispell会给出 形式的错误“尚无法处理非交互式使用”。在某些情况下。

(作为一个方面不行,我非常希望从Java使用的ProcessBuilder类ispell的编程方式调用,并且无需庆典。同样的错误似乎然而,纠缠了这种方法。)

问题

为什么ispell会给出错误“无法处理非交互式使用”。在某些情况下,当从包含read方法的循环中调用bash时,在其他情况下不会调用,如下面的代码示例所示?

的下面最小的代码的示例创建两个小文件 (testFileOne.txttestFileTwo.txt)和含有两个创建的文件(testFilesListTemp.txt)的路径中的文件。 接下来,ispell以三种不同的方式调用testFilesListTemp.txt: 1.借助“cat” 2.首先将名称作为字符串收集,然后遍历收集字符串中的子字符串,然后调用ispell为他们每个人。 3.通过循环播放内容testFilesListTemp.txt直接和 调用ispell提取路径。

对于某些重复,第三种方法不起作用,并产生错误 “无法处理非交互式使用。”。为什么这个错误 发生,以及如何防止,和/或有没有错误的第三种方法的另一种变化 ?

#!/bin/bash 

#ispell ./testFiles/ispellTestFile1.txt 

# Creating two small files and a file with file paths for testing 
printf "file 1 contents" > testFileOne.txt 
printf "file 2 contents. With a spelling eeeeror." > testFileTwo.txt 
printf "./testFileOne.txt\n./testFileTwo.txt\n" > testFilesListTemp.txt 

COLLECTED_LATEX_FILE_NAMES_FILE=testFilesListTemp.txt 


# Approach 1: produce list of file names with cat and 
# pass as argumentto ispell 
# WORKS 
ispell $(cat $COLLECTED_LATEX_FILE_NAMES_FILE) 

# Second approach, first collecting file names as long string, 
# then looping over substrings and calling ispell for each one of them 
FILES="" 
while read p; do 
echo "read file $p" 
FILES="$FILES $p" 
done < $COLLECTED_LATEX_FILE_NAMES_FILE 

printf "files list: $FILES\n" 

for latexName in $FILES; do 
    echo "filename: $latexName" 
    ispell $latexName 
done 


# Third approach, not working 
# ispell compmlains in this case about not working in non-interactive 
# mode 
#: "Can't deal with non-interactive use yet." 
while read p; do 
    ispell "$p" 
done < $COLLECTED_LATEX_FILE_NAMES_FILE 

回答

0

第三个示例不起作用,因为您重定向了标准输入。 ispell需要终端和用户交互。当你写这样的代码:

while read p; do 
    ispell "$p" 
done < $COLLECTED_LATEX_FILE_NAMES_FILE 

是从标准输入任何程序循环内阅读一切将从$COLLECTED_LATEX_FILE_NAMES_FILE文件服用。 ispell检测到并拒绝操作。但是,您可以使用“描述重定向”使read p从文件中读取,ispell "$p"从“真实”终端读取。只要做到:

exec 3<&0 
while read p; do 
    ispell "$p" 0<&3 
done < $COLLECTED_LATEX_FILE_NAMES_FILE 

exec 3<&0“副本”(保存)的标准输入(0,“终端”)来描述3.而从描述符,通过输入标准输入(0)以后您重定向到ispell0<&3(如果你喜欢,你可以省略0)。