2017-05-30 75 views
-1

我在編程競賽中(我不知道爲什麼,我幾乎不知道任何高級Python),因爲我的老師認爲這是一個好主意。其中一個練習項目是創建一個包含6個函數的字符串編輯器,分別是Insert,Delete,Reverse,Update/Replace,Append和Prepend一個字符串。對於輸入的語法應該是這樣的:Python字符串編輯器

computer I 3 BIT 

comper 

輸出所以第一部分是編輯字符串,第二個是操作(I可以進行插入,爲d刪除,R表示反向等)。問題是,其餘的東西是不同的。對於I,D和R,共有4個部分。第三是操作的起點。第四個是爲I插入的字符串,以及爲D刪除的字符數,R可以處理的字符數。但是,更新/替換包含5個部分。字符串,修飾符(U),開始位置,要替換的字符數以及要替換的子字符串。

同樣,Append和Prepend有3個部分。原始字符串,修飾符(A或P)以及要添加或附加的子字符串。

到目前爲止,我已經拿出下面的代碼。

while True: 
    Full_String = input("Please enter a string, modifier, start character, and iteration modifier: ") 
    string, modifier, start, itermod = Full_String.split (" ") 
    print (string) 
    print (modifier) 
    print (start) 
    print (itermod) 

打印命令只是爲了確保字符串正確拆分。然而,每當我嘗試使用某些操作所需的3或5個參數時,我會得到一個ValueError。通常,我可以添加Try-Except塊來捕獲錯誤,但我無法弄清楚如何在沒有2級用戶輸入的情況下執行此操作。

那麼,無論如何,我該如何設法將這個問題歸結爲一行輸入?對於每個輸入應類似於以下:

插入:字符串I 2新

刪除:字符串d 2 3

反向:字符串R 2 3

更新/替換:字符串ù 2 3個新(字符串的長度必須是不管以前的說法是,即3個新的,4日消息,5大)

附加:字符串的新

Prepen d:字符串P新

任何幫助都非常感謝。

+0

使用拆分,但將結果保留在單個列表中:'result = Full_String.split(「」)'。然後,你可以參考'result [3]'和'result [4]'等,這取決於result [0]的值。 –

+0

你需要看看*加星號的表達*。 –

+0

通常,在你的問題中追加堆棧跟蹤(這種情況下的ValueError)是有幫助的 – rinderwahn

回答

0

如果我想要乾淨的代碼,我會親自解決這個問題,如:

full_string = input("Please enter a string, modifier, start character, and iteration modifier:") 
command = full_string.strip().split() # doesn't care about amount of whitespace used 

if command[1] == 'I': 
    # insert specific instructions 
    string, _, start, itermod = command 
    ... 
... 
elif command[1] == 'R': 
    # replace specific 
    string, _, index1, index2, new_string = command 
... 

製作,每串指令的情況下。

可以或許也可以使用如在註釋中描述的星號的語法:

string, command, *args = full_string.split(" ") # args is now a list of arguments 

但在python2這不會工作

更新:由布魯諾desthuilliers指出,理想情況下你會使用每種情況下的功能。雖然我個人更喜歡避免會導致額外複雜性的構造(如dictionairies /函數指針)。

如果要使用額外的功能,我可能會做這樣的自己:

def do_insert(string, start, itermod): 
    ... program logic ... 

def do_update(string, index1, index2, replacement): 
    ... program logic ... 

... 

while True: 
    full_string = input("Please enter a string, modifier, start character, and iteration modifier:") 

    # doesn't care about amount of whitespace used 
    command = full_string.strip().split() 

    # split the command into string, modifier and additional variable args 
    string, modifier, extra_args = command[0], command[1], command[2:] 

    if modifier == 'I': 
     do_insert(string, *extra_args) 
    elif modifier == 'D': 
     do_delete(string, *extra_args) 
    elif modifier == 'U': 
     do_update(string, *extra_args) 
    ... 

這裏的*extra_args將插入的extra_args的元素作爲參數。 例如調用func(a, b, *[1,2,3])將被轉換爲func(a, b, 1, 2, 3)

+1

「乾淨的」代碼會抽象出參數解析,因此主循環不必關心它。事實上,明星語法不適用於Python 2. –

+0

我同意理想情況下,應該使用方法。雖然我覺得這個目標相對簡單,但更簡單的設置會更好,尤其是如果你只是一個初學者。雖然優雅,但您的解決方案可能有點複雜。 –

+0

「方法」(以及類等)不是唯一可用的抽象...只是使用基本的東西(函數,字典,列表,元組),你已經可以使主循環完全通用的Wrt /操作特性,參考我的答案。 –

0

輸入內容以及應如何解析取決於命令,所以你應該有每個命令一個解析器。爲此,可以使用一個字典映射命令做(「I」,「d」,「R」等)的解析器功能:

def parse_insert(args): 
    # code to parse arguments for an insert 
    return { 
     "start": args[0], 
     "itermod": args[1] 
    } 



def parse_delete(args): 
    # code to parse argumenst for a delete 
    # cf example above 

# etc 

PARSERS = { 
    "I" : parse_insert, 
    "D" : parse_delete, 
    # etc 
} 


def main(): 
    while True: 
     full_string = input("Please enter a string, modifier, start character, and iteration modifier: ") 
     parts = full_string.split (" ") 
     line = parts[0] 
     parser = PARSERS[parts[1]] 
     op_args = parser(parts[2:]) 

你可能需要操作類似,即:

def do_delete(line, start, itermod): 
    # code here 


def do_insert(line, ....) 
    # idem 


OPERATIONS = { 
    "D" : do_delete, 
    "I": do_insert, 
    # etc 
} 



def main(): 
    while True: 
     full_string = input("Please enter a string, modifier, start character, and iteration modifier: ") 
     parts = full_string.split (" ") 
     line = parts[0] 
     opid = parts[1] 
     parser = PARSERS[opid] 
     op_args = parser(parts[2:]) 
     print(line, opid, op_args) 
     op = OPERATORS[opid] 
     result = op(line, **op_args) 
     print(result) 

這仍然需要一些錯誤處理,但這應該讓你開始。

0

讓我們來解決你的分裂問題,你可以自己編寫剩餘的程序。 split()需要第二個參數來告訴它可能會分裂多少次。你的編輯命令有三個固定的參數,其次是不同的東西。所以,你可以分成最多三個部分,檢查命令,並繼續酌情:

string, cmd, rest = full_string.split(" ", 2) 
if cmd == "I": 
    start, toinsert = rest.split(" ", 1) # `toinsert` string could contain spaces? 
elif cmd == "R": 
    <etc.> 

或者,你可以收集可變長度部分到一個列表,稍後解釋。但是,如果允許插入的字符串包含空格,這是非理想的,因爲它們會在字符串中造成額外的中斷。

string, cmd, start, *rest = full_string.split() 

這裏,rest變得與額外的參數(如果有的話)的列表,並且可以基於命令再次重新分配。

if cmd == "I": 
    toinsert = rest[0] 
elif cmd == "R": 
    <etc.>