open () ใน Python ไม่ได้สร้างไฟล์หากไม่มีอยู่


660

เป็นวิธีที่ดีที่สุดในการเปิดไฟล์เป็นอ่าน / เขียนถ้ามันมีอยู่หรือถ้ามันไม่ได้แล้วสร้างมันขึ้นมาและเปิดเป็นอ่าน / เขียน? จากสิ่งที่ฉันอ่านfile = open('myfile.dat', 'rw')ควรทำสิ่งนี้ใช่ไหม

มันไม่ทำงานสำหรับฉัน (Python 2.6.2) และฉันสงสัยว่ามันเป็นปัญหาของรุ่นหรือไม่ควรทำงานเช่นนั้นหรืออะไร

บรรทัดล่างคือฉันแค่ต้องการทางออกสำหรับปัญหา ฉันอยากรู้เกี่ยวกับสิ่งอื่น ๆ แต่ทั้งหมดที่ฉันต้องการคือวิธีที่ดีในการทำส่วนเปิด

ไดเรกทอรีที่ปิดล้อมนั้นเขียนได้โดยผู้ใช้และกลุ่มไม่ใช่คนอื่น (ฉันอยู่ในระบบ Linux ... ดังนั้นสิทธิ์ 775 กล่าวอีกนัยหนึ่ง) และข้อผิดพลาดที่แน่นอนคือ:

IOError: ไม่มีไฟล์หรือไดเรกทอรีดังกล่าว


2
ดังที่ S.Mark กล่าวถึงสิ่งนี้ควร "แค่ทำงาน" ไดเรกทอรีที่ปิดล้อมสามารถเขียนได้?
Rakis

10
"มันไม่ทำงานสำหรับฉัน"? หมายความว่าอย่างไรโดยเฉพาะ โปรดระบุข้อความแสดงข้อผิดพลาดที่เกิดขึ้นจริง
S.Lott

5
คำตอบของ muksie ทำงานด้านล่าง (และ baloo เกินไปสำหรับเรื่องนั้น) แต่เพื่อความสมบูรณ์ dir ที่ล้อมรอบนั้นเขียนได้โดยผู้ใช้และกลุ่มไม่ใช่คนอื่น (im บนระบบ linux ... ดังนั้นสิทธิ์ 775 ในคำอื่น ๆ ) และแน่นอน ข้อผิดพลาดคือ IOError: ไม่มีไฟล์หรือไดเรกทอรีดังกล่าว ขอบคุณสำหรับความช่วยเหลือ
trh178

@ S.Lott: เสร็จแล้ว ขอโทษด้วยกับเรื่องนั้น.
trh178

ตรวจสอบให้แน่ใจว่าโฟลเดอร์นำทั้งหมดของที่fileมีอยู่
Jason Goal

คำตอบ:


804

คุณควรใช้openกับw+โหมด:

file = open('myfile.dat', 'w+')

109
wตัดทอนไฟล์ที่มีอยู่ เอกสาร: โหมด'r+', 'w+'และ'a+'เปิดไฟล์สำหรับการอัปเดต (ทราบว่า'w+'ตัดทอนไฟล์)
SilentGhost

4
นี่เป็นการหลอกลวง ขอบคุณ. ตอนนี้ฉันรู้สึกเหมือนคนงี่เง่าที่ไม่ได้อ่านสเป็ค ฉันไม่คิดว่า 'rw' เป็นที่ยอมรับแม้แต่ที่นั่น ฉันต้องคิดอย่างอื่น
trh178

72
โปรดทราบว่าเครื่องหมาย + จะสร้างไฟล์หากไม่มีอยู่และจะค้นหาไฟล์จนจบ ดังนั้นหากคุณอ่านทันทีหลังจากเปิดวิธีนี้คุณจะไม่ได้อะไรเลย คุณจำเป็นต้องค้นหากลับไปที่จุดเริ่มต้นก่อน: f.seek (0)
Nick Zalutskiy


120
นี่ไม่ใช่ทางออก ปัญหาคือไดเร็กทอรี สคริปต์ไม่มีสิทธิ์ในการสร้างไฟล์ในไดเรกทอรีนั้นหรือไม่มีไดเรกทอรีอยู่ open('myfile.dat', 'w')เพียงพอแล้ว
Daniel F

137

ข้อดีของวิธีการต่อไปนี้คือไฟล์ถูกปิดอย่างเหมาะสมในตอนท้ายของบล็อกแม้ว่าจะมีข้อยกเว้นเกิดขึ้น มันเทียบเท่ากับtry-finallyแต่สั้นกว่ามาก

with open("file.dat","a+") as f:
    f.write(...)
    ...

+เปิดไฟล์สำหรับการต่อท้ายและการอ่าน ตัวชี้ไฟล์อยู่ท้ายไฟล์หากไฟล์นั้นมีอยู่ ไฟล์จะเปิดขึ้นในโหมดต่อท้าย หากไฟล์ไม่มีอยู่มันจะสร้างไฟล์ใหม่สำหรับการอ่านและการเขียน - โหมดไฟล์ Python

find () วิธีการตั้งค่าตำแหน่งปัจจุบันของไฟล์

f.seek(pos [, (0|1|2)])
pos .. position of the r/w pointer
[] .. optionally
() .. one of ->
  0 .. absolute position
  1 .. relative position to current
  2 .. relative position from end

อนุญาตให้ใช้เฉพาะอักขระ "rwab +" เท่านั้น ต้องมีตรงหนึ่งของ "RWA" - ดูกองมากเกินคำถามหลามรายละเอียดรูปแบบไฟล์


1
ฉันลองด้วย open (ชื่อไฟล์, 'a +') เป็น myfile: และรับ IOError: [Errno 2] ไม่มีไฟล์หรือไดเรกทอรี: - ทำไมมันไม่สร้างไฟล์?
Loretta

@ Loretta คุณได้ตรวจสอบค่าของfilename?
Qwerty

ใช่ฉันทำ. มันเป็นสตริง Unicode ฉันยังลองเปิด ('{}. txt'.format (ชื่อไฟล์),' a + ') เป็น myfile:
Loretta

ฉันไม่ได้ใช้เส้นทาง และฉันพยายามเปิด ('test.txt', 'a +') มันได้รับการยกเว้น 'TypeError: บังคับให้ Unicode: ต้องการสตริงหรือบัฟเฟอร์, พบไฟล์' ในบรรทัดถ้า os.stat (myfile) .st_size == 0:
Loretta

คุณต้องกำหนดการเข้ารหัสอย่างถูกต้องเพื่อให้สิ่งนี้ทำงานได้ stackoverflow.com/q/728891/3701431
Sergiy Kolodyazhnyy

31

แนวปฏิบัติที่ดีคือการใช้สิ่งต่อไปนี้:

import os

writepath = 'some/path/to/file.txt'

mode = 'a' if os.path.exists(writepath) else 'w'
with open(writepath, mode) as f:
    f.write('Hello, world!\n')

18
การทดสอบไฟล์ก่อนเปิดเป็นเรื่องที่ไม่ดีเนื่องจากอาจนำไปสู่สภาวะการแข่งขัน (ไฟล์ถูกลบก่อนที่จะเปิด) เงื่อนไขการแย่งชิงบางครั้งสามารถใช้เพื่อทำลายช่องโหว่ในระบบ โหมด "a +" เป็นวิธีที่ดีที่สุดในการเปิดไฟล์: สร้างไฟล์ใหม่และผนวกเข้ากับไฟล์ที่มีอยู่ อย่าลืมห่อในลอง / ยกเว้น
sleblanc

โหมดการเขียนหรือผนวกไม่มีความสนใจ หากไฟล์ไม่มีอยู่โหมดต่อท้ายจะสร้างขึ้น
Jean-François Fabre


25
>>> import os
>>> if os.path.exists("myfile.dat"):
...     f = file("myfile.dat", "r+")
... else:
...     f = file("myfile.dat", "w")

r + หมายถึงอ่าน / เขียน


57
นี่คือ Unpythonic แทนที่จะตรวจสอบว่าไฟล์ที่มีอยู่ครั้งแรกหนึ่งควรถือว่ามันไม่ก่อนแล้วจัดการกับกรณีที่มันไม่ได้
แบล็กไลท์ส่องแสง

38
ยิ่งรหัสนี้มีแนวโน้มที่จะแย่ลง ดังนั้นหลังจากตรวจสอบว่ามีไฟล์อยู่หรือไม่กระบวนการอาจถูกขัดจังหวะและกระบวนการอื่นสามารถสร้างไฟล์นี้ได้
antibus

คุณจะต้องตั้งค่าสถานะ "w +" เพื่อให้ไฟล์ทั้งสองอยู่ในโหมดอ่านและเขียน
The Matt

14

ตั้งแต่ python 3.4 คุณควรใช้pathlibเพื่อ "สัมผัส" ไฟล์
มันเป็นคำตอบที่สวยงามกว่าคำตอบในหัวข้อนี้

from pathlib import Path

filename = Path('myfile.txt')
filename.touch(exist_ok=True)  # will create file, if it exists will do nothing
file = open(filename)

สิ่งเดียวกันกับไดเรกทอรี:

filename.mkdir(parents=True, exist_ok=True)

2
touchจะอัปเดตเวลาที่แก้ไขล่าสุดเมื่อใช้
David Parks

@DavidParks จุดที่ดีเพียงแค่ทดสอบและเป็นจริงในระบบไฟล์ ext4 และ python3.7.2 ฉันไม่คิดว่ามันตั้งใจหรือพฤติกรรมที่ต้องการบางทีมันเป็นบั๊กกับงูหลาม?
Granitosaurus

3
สิ่งเดียวกันเมื่อใช้touchที่บรรทัดคำสั่งใน linux ดังนั้นฉันคิดว่ามันเป็นพฤติกรรมที่ตั้งใจ
David Parks


9
'''
w  write mode
r  read mode
a  append mode

w+  create file if it doesn't exist and open it in write mode
r+  open for reading and writing. Does not create file.
a+  create file if it doesn't exist and open it in append mode
'''

ตัวอย่าง:

file_name = 'my_file.txt'
f = open(file_name, 'w+')  # open file in write mode
f.write('python rules')
f.close()

ฉันหวังว่านี่จะช่วยได้. [FYI ใช้ python เวอร์ชั่น 3.6.2]


6

open('myfile.dat', 'a') ทำงานได้สำหรับฉันได้ดี

ใน py3k รหัสของคุณเพิ่มขึ้นValueError:

>>> open('myfile.dat', 'rw')
Traceback (most recent call last):
  File "<pyshell#34>", line 1, in <module>
    open('myfile.dat', 'rw')
ValueError: must have exactly one of read/write/append mode

ในหลาม 2.6 IOErrorมันจะเพิ่ม


6

ใช้:

import os

f_loc = r"C:\Users\Russell\Desktop\myfile.dat"

# Create the file if it does not exist
if not os.path.exists(f_loc):
    open(f_loc, 'w').close()

# Open the file for appending and reading
with open(f_loc, 'a+') as f:
    #Do stuff

หมายเหตุ: ไฟล์จะต้องปิดหลังจากที่คุณเปิดไฟล์และด้วย context manager เป็นวิธีที่ดีในการให้ Python ดูแลสิ่งนี้ให้คุณ


6

คุณต้องการทำอะไรกับไฟล์ เขียนเฉพาะมันหรือทั้งอ่านและเขียน?

'w', 'a'จะช่วยให้การเขียนและจะสร้างไฟล์ถ้ามันไม่ได้อยู่

หากคุณต้องการอ่านจากไฟล์ไฟล์นั้นจะต้องมีอยู่ก่อนที่จะเปิด คุณสามารถทดสอบการมีอยู่ของมันก่อนที่จะเปิดหรือใช้ลอง / ยกเว้น


5
การทดสอบการมีอยู่ก่อนที่จะเปิดอาจแนะนำสภาพการแข่งขัน อาจไม่ใช่เรื่องใหญ่ในกรณีนี้ แต่เป็นสิ่งที่ควรคำนึงถึง
Daniel Hepper

1
"ถ้าคุณต้องการอ่านจากไฟล์ไฟล์นั้นจะต้องมีอยู่ก่อนที่จะเปิด" ขอขอบคุณที่ช่วยรักษาสติของฉัน
Brian Peterson

5

ฉันคิดว่ามันไม่ได้r+ rwฉันเป็นแค่ผู้เริ่มต้นและนั่นคือสิ่งที่ฉันเห็นในเอกสารประกอบ


4

วาง w + เพื่อเขียนไฟล์ตัดทอนถ้ามีอยู่ r + เพื่ออ่านไฟล์สร้างไฟล์ถ้าไม่มีอยู่ แต่ไม่ใช่การเขียน (และส่งคืนค่า null) หรือ + สำหรับสร้างไฟล์ใหม่หรือต่อท้ายไฟล์ที่มีอยู่


1

ดังนั้นคุณต้องการเขียนข้อมูลไปยังไฟล์ แต่ถ้ามันยังไม่มีอยู่?

ปัญหานี้แก้ไขได้อย่างง่ายดายโดยใช้โหมด x ที่รู้จักกันน้อยเพื่อเปิด () แทนโหมด w ปกติ ตัวอย่างเช่น:

 >>> with open('somefile', 'wt') as f:
 ...     f.write('Hello\n')
...
>>> with open('somefile', 'xt') as f:
...     f.write('Hello\n')
...
 Traceback (most recent call last):
 File "<stdin>", line 1, in <module>
FileExistsError: [Errno 17] File exists: 'somefile'
  >>>

หากไฟล์เป็นโหมดไบนารีให้ใช้โหมด xb แทน xt


1

หากคุณต้องการเปิดอ่านและเขียนฉันถือว่าคุณไม่ต้องการตัดทอนเมื่อคุณเปิดและคุณต้องการอ่านไฟล์ทันทีหลังจากเปิด ดังนั้นนี่คือทางออกที่ฉันใช้:

file = open('myfile.dat', 'a+')
file.seek(0, 0)

0

อาจจะช่วยได้

แรกนำเข้าโมดูล os ลงในไฟล์ py ของคุณ

import os

จากนั้นสร้างตัวแปรชื่อ save_file และตั้งเป็นไฟล์ที่คุณต้องการสร้าง html หรือ txt ในกรณีนี้เป็นไฟล์ txt

save_file = "history.txt"

จากนั้นกำหนดฟังก์ชั่นที่จะใช้วิธีการไฟล์ os.path.is เพื่อตรวจสอบว่ามีไฟล์อยู่หรือไม่และจะสร้างไฟล์หรือไม่

def check_into():
if os.path.isfile(save_file):
    print("history file exists..... \nusing for writting....")
else:
    print("history file not exists..... \ncreating it..... ")
    file = open(save_file, 'w')
    time.sleep(2)
    print('file created ')
    file.close()

และเมื่อมีการเรียกใช้ฟังก์ชั่นล่าสุด

check_into()

-2
import os, platform
os.chdir('c:\\Users\\MS\\Desktop')

try :
    file = open("Learn Python.txt","a")
    print('this file is exist')
except:
    print('this file is not exist')
file.write('\n''Hello Ashok')

fhead = open('Learn Python.txt')

for line in fhead:

    words = line.split()
print(words)
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.