2013-03-19 126 views
5

我試圖覆蓋文件。我在此基礎上Read and overwrite a file in Python如何覆蓋Python中的文件?

我的答案來完成我的代碼:

<select class="select compact expandable-list check-list" 
    ONCHANGE="location = this.options[this.selectedIndex].value;"> 
    <option value="{% url envelopes:auto_sort %}?sort_by=custom"> 
     Custom order 
    </option> 
    <optgroup label="Category"> 
     <option value="{% url envelopes:auto_sort %}?sort_by=cat_asc"> 
      Ascending order 
     </option> 
     <option value="{% url envelopes:auto_sort %}?sort_by=cat_desc"> 
      Descending order 
     </option> 
    </optgroup> 
</select> 

def auto_sort(request): 
    sort_by = request.GET.get('sort_by', None) 
    if sort_by: 
     temp_path = "{0}/file.txt".format(settings.SITE_ROOT) 

     f=open(temp_path,'r+') 
     text = f.read() 
     text = re.sub('cat_asc', 'cat_desc', text) 
     f.seek(0) 
     f.write(text) 
     f.truncate() 
     f.close(); 

     handle=open(temp_path,'w+') 
     handle.write(sort_by) 
     handle.close(); 

    return HttpResponseRedirect(reverse('envelopes:editor')) 

我目前的代碼輸出:

該文件包含cat_desc當我嘗試爲custom重寫一遍。它改寫爲customc。注意c最後,它只能是custom

這裏是我想要實現:

  1. 我寫的文件,例如,cat_desc
  2. 如果我想再次寫,例如custom,該cat_desc必須拆除並換成custom
+3

哪條線發生的錯誤? – Serdalis 2013-03-19 04:28:52

+0

http://docs.python.org/2/library/re.html#re.sub re.sub接受三個字符串參數'pattern'/'replacement','string'。第四個參數(你的「文本」參數)必須是一個指定計數的數字 – RedBaron 2013-03-19 04:48:06

+0

're.sub' _supposed_要做什麼?參數在問題和回溯中的順序不同! – 2013-03-19 04:48:11

回答

4

根據修改後的問題,也許這樣的事情會更簡單

def auto_sort(request): 
    sort_by = request.GET.get('sort_by', None) 
    if sort_by: 
     temp_path = "{0}/file.txt".format(settings.SITE_ROOT) 
     #Set new_text to whatever you want based on your logic 
     new_text = 'custom' 
     f=open(temp_path,'w') 
     f.write(new_text) 
     f.close(); 

     handle=open(temp_path,'w+') 
     handle.write(sort_by) 
     handle.close(); 

    return HttpResponseRedirect(reverse('envelopes:editor')) 
+0

我再次收到錯誤TypeError:一個整數是必需的。這是之前的錯誤。 – catherine 2013-03-19 05:17:33

+0

刪除re.sub部分。你不需要它 – RedBaron 2013-03-19 05:18:07

+0

它現在正在工作,我會測試這個 – catherine 2013-03-19 05:22:05

-1

你可以複製和粘貼完整的錯誤回到

嘗試:

def auto_sort(request): 
    sort_by = request.GET.get('sort_by', None) 
    if sort_by: 
     temp_path = "{0}/file.txt".format(settings.SITE_ROOT) 
     f=open(temp_path,'r') 
     text = f.read() 
     text = re.sub('custom', 'cat_asc', 'cat_desc', text) 
     f.close(); 
     handle=open(temp_path,'w') 
     handle.write(sort_by) 
     handle.close(); 
    return HttpResponseRedirect(reverse('envelopes:editor')) 
+0

再次出現同樣的錯誤 – catherine 2013-03-19 04:40:29

5

新anwser ...

你傳遞textre.sub的第四個參數。這應該是一個int

Help on function sub in module re: 

sub(pattern, repl, string, count=0, flags=0) 
    Return the string obtained by replacing the leftmost 
    non-overlapping occurrences of the pattern in string by the 
    replacement repl. repl can be either a string or a callable; 
    if a string, backslash escapes in it are processed. If it is 
    a callable, it's passed the match object and must return 
    a replacement string to be used. 

老答案...

也許你正在做

from os import open 

這是一個不同的(下級)開放,你想只需使用內置的開放(你不需要輸入任何東西使用它)

這裏是一個EXA做錯了,並得到你的錯誤信息

>>> from os import open 
>>> open("some_path", "r+") 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
TypeError: an integer is required 

也要覆蓋文件,你需要打開「w +」。 「R」代表讀

+0

我沒有使用'從os導入打開' – catherine 2013-03-19 04:39:20

+0

@catherine,好的。問題與覆蓋文件無關,它是使用're.sub' – 2013-03-19 04:46:47

2

您的問題無關,與寫入文件。

回溯告訴你,此行是罪魁禍首:

File "/home/cath/src/envelopebudget/envelopebudget/settings/../apps/envelopes/views.py" in auto_sort 
    357.   text = re.sub('cat_desc', 'cat_asc', 'custom', text) 

如果你看一下re.sub方法,你調用一個錯誤:

re.sub(pattern, repl, string, count=0, flags=0) 

你傳遞'cat_desc'pattern,'cat_asc'作爲repl,'custom'作爲string和作爲count作爲text。這沒有任何意義。 re.sub預計count是一個整數,並且您給它一個字符串。

+0

的掃描儀確定我已經擦除了該定製,現在它可以工作。但我試圖實現的是完全重寫文件。 – catherine 2013-03-19 04:47:50

+0

@catherine:好的,但如果這不起作用,你會遇到一個完全不同的問題,你需要告訴我們詳細情況,最好是在一個新問題中。 – abarnert 2013-03-19 05:03:52

+0

它允許創建新的問題嗎?我的問題是覆蓋作爲標題的文件。 – catherine 2013-03-19 05:09:53

5

對於新的問題:

試圖覆蓋就地文件基本上是不可能的,除非你有確切的相同長度的新字節字符串替換字節串。如果您將'cat_desc'替換爲'cat_asc',那麼您將以'cat_ascc'結束。

你在做什麼 - 在'r+'模式下打開它,讀取整個文件,處理它,將seek寫入0,然後寫入整個文件 - 確實有效。但這不是做事的最佳方式。

無論如何,你的問題是,在你做這件事之後,你需要在'w+'模式(截斷文件)中打開完全相同的路徑,然後寫一些不同的東西。所以,無論你寫什麼現在都消失了。

解決方案是...不這樣做。我不確定你想要做什麼,但可能不是這樣。

同時,重寫文件的最佳方式是「原子寫入溫度和重命名」習語。這保證你永遠不會損壞文件,你可以得到新文件或者仍舊保留舊文件。這也意味着你不必將整個文件保存在內存中;你可以一點一滴地去。這很簡單...如果你不關心Windows。它的工作原理是這樣的:

with tempfile.NamedTemporaryFile(delete=False) as outfile: 
    with open(inpath) as infile: 
     # copy from infile to outfile, changing things as you go 
    os.rename(outfile.name, inpath) 

不幸的是,在Windows上開展這項工作非常痛苦。當它仍然處於打開狀態時,您不能移動outfile,並且您不能在with聲明之外訪問它,並且最重要的是,您不能僅使用outfile覆蓋infile;你必須做一個複雜的洗牌。除非您願意要求Vista/2008並直接調用Win32 API,否則它永遠不會是完全原子的。

+0

謝謝我現在明白爲什麼我會得到該輸出 – catherine 2013-03-19 05:26:42