Передача мета-символов Python в качестве аргументов из командной строки
я делаю программу Python, которая будет анализировать поля в некоторых входных строках. Я хотел бы позволить пользователю ввести разделитель полей в качестве опции из командной строки. Я использую optparse для этого. Я сталкиваюсь с проблемой, которая вводит что-то вроде t отделится буквально на t, а не на вкладке, что и я хочу. Я уверен, что это вещь Python, а не оболочка, так как я пробовал каждую комбинацию кавычек, обратных косых черт и t's, что я могу думать из.
если бы я мог сделать optparse чтобы аргумент был простым вводом (есть ли такая вещь?), а не raw_input, Я думаю, что это сработает. Но я понятия не имею, как это сделать.
я также пробовал различные замены и трюки с регулярным выражением, чтобы превратить строку из двух символов "t" на вкладке один символ, но без успеха.
пример, где input.txt - это:
field 1[tab]fieldt2
(Примечание: [tab] закладка характера и fieldt2 - это 8 символов)
parseme.py:
#!/usr/bin/python
from optparse import OptionParser  
parser = OptionParser()  
parser.add_option("-d", "--delimiter", action="store", type="string",  
    dest="delimiter", default='t')  
parser.add_option("-f", dest="filename")  
(options, args) = parser.parse_args()  
Infile = open(options.filename, 'r')  
Line = Infile.readline()  
Fields = Line.split(options.delimiter)  
print Fields[0]  
print options.delimiter  
Infile.close()  
это дает мне:
$ parseme.py -f input.txt  
field 1  
[tab]
Эй, отлично, настройка по умолчанию работала правильно. (Да, я знаю, что могу просто сделать T по умолчанию и забыть об этом, но я хотел бы знать, как справиться с этим типом проблемы.)
$ parseme.py -f input.txt -d 't'  
field 1[tab]field  
t
это не то, что я хочу.
4 ответов
быстрый и грязный способ, чтобы eval, вот так:
eval(options.delimiter, {}. {})
дополнительные пустые дикты существуют для предотвращения случайного clobbering вашей программы.
решение его из вашего скрипта:
options.delimiter = re.sub("\\t","\t",options.delimiter)
вы можете адаптировать re, чтобы соответствовать более экранированным символам (\n, \r и т. д.)
другой способ решить проблему за пределами python:
когда вы вызываете свой скрипт из оболочки, сделайте это так:
parseme.py -f input.txt -d '^V<tab>'
^V означает "нажмите Ctrl+V"
затем нажмите клавишу обычной вкладки
это правильно передаст символ вкладки в ваш скрипт python;
на callback опция-хороший способ справиться с сложными случаями:
parser.add_option("-d", "--delimiter", action="callback", type="string",
                  callback=my_callback, default='\t')
С соответствующей функцией (должна быть определена до парсер, потом):
def my_callback(option, opt, value, parser):
    val = value
    if value == '\t':
        val = '\t'
    elif value == '\n':
        val = '\n'
    parser.values.delimiter = val
вы можете проверить это работает через командную строку: python test.py -f test.txt -d \t (нет цитаты вокруг \t, они бесполезны).
он имеет преимущество обработки опции через модуль "optparse", а не через постобработку результатов анализа.
