Правильный способ записи строки в файл?

Я привык делать print >>f, "hi there"

Однако, кажется, что print >> становится устаревшим. Каков рекомендуемый способ сделать линию выше?

Update: Что касается всех этих ответов с помощью "\n"... является ли это универсальным или Unix-специфическим? IE, должен ли я делать "\r\n" в Windows?

Ответ 1

Это должно быть просто:

with open('somefile.txt', 'a') as the_file:
    the_file.write('Hello\n')

Из документа:

Не используйте os.linesep в качестве ограничителя строк при записи файлов, открытых в текстовом режиме (по умолчанию); вместо этого используйте один "\n" на всех платформах.

Некоторое полезное чтение:

Ответ 2

Вы должны использовать функцию print(), доступную с Python 2.6 +

from __future__ import print_function  # Only needed for Python 2
print("hi there", file=f)

Для Python 3 вам не нужен import, так как функция print() по умолчанию.

Альтернативой может быть использование:

f = open('myfile', 'w')
f.write('hi there\n')  # python will convert \n to os.linesep
f.close()  # you can omit in most cases as the destructor will call it

Цитата из документации по Python относительно новых строк:

На выходе, если новая строка - None, любые написанные символы '\n' переводятся в разделитель строк по умолчанию системы, os.linesep. Если новая строка '', перевод не выполняется. Если новая строка является любым другим правовым значением, любые написанные символы '\n' переводятся в заданную строку.

Ответ 3

Документы Python рекомендуют так:

with open('file_to_write', 'w') as f:
    f.write('file contents')

Так я обычно так и делаю :)

Заявление от docs.python.org:

Это хорошая практика, чтобы использовать "с" ключевым словом при работе с файловыми объектами. Преимущество этого заключается в том, что файл правильно закрывается после завершения его набора, даже если по пути возникает исключение. Это также намного короче, чем написание эквивалентных блоков try-finally.

Ответ 4

Что касается os.linesep:

Вот точный неотредактированный сеанс интерпретатора Python 2.7.1 в Windows:

Python 2.7.1 (r271:86832, Nov 27 2010, 18:30:46) [MSC v.1500 32 bit (Intel)] on
win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import os
>>> os.linesep
'\r\n'
>>> f = open('myfile','w')
>>> f.write('hi there\n')
>>> f.write('hi there' + os.linesep) # same result as previous line ?????????
>>> f.close()
>>> open('myfile', 'rb').read()
'hi there\r\nhi there\r\r\n'
>>>

В Windows:

Как и ожидалось, os.linesep делает NOT результат с тем же результатом, что и '\n'. Нет никакого способа добиться такого же результата. 'hi there' + os.linesep эквивалентен 'hi there\r\n', который НЕ эквивалентен 'hi there\n'.

Это просто: используйте \n, который будет автоматически переведен на os.linesep. И это было так просто с первого порта Python в Windows.

Нет смысла использовать os.linesep в системах, отличных от Windows, и это приводит к неправильным результатам в Windows.

НЕ ИСПОЛЬЗУЙТЕ os.linesep!

Ответ 5

Я не думаю, что есть "правильный" способ.

Я бы использовал:

with open ('myfile', 'a') as f: f.write ('hi there\n')

В memoriam Тим Туди.

Ответ 6

В Python 3 это функция, но в Python 2 вы можете добавить это в начало исходного файла:

from __future__ import print_function

Затем вы делаете

print("hi there", file=f)

Ответ 7

Если вы пишете много данных, а скорость - это проблема, вы, вероятно, должны пойти с f.write(...). Я сделал быстрое сравнение скорости, и это было значительно быстрее, чем print(..., file=f) при выполнении большого количества записей.

import time    

start = start = time.time()
with open("test.txt", 'w') as f:
    for i in range(10000000):
        # print('This is a speed test', file=f)
        # f.write('This is a speed test\n')
end = time.time()
print(end - start)

В среднем write завершено на 2.45 с на моей машине, тогда как print заняло примерно 4 раза (9,76 с). При этом в большинстве реальных сценариев это не будет проблемой.

Если вы решите пойти с print(..., file=f), вы, вероятно, обнаружите, что хотите время от времени подавлять новую строку или заменять ее чем-то другим. Это можно сделать, установив необязательный параметр end, например.

with open("test", 'w') as f:
    print('Foo1,', file=f, end='')
    print('Foo2,', file=f, end='')
    print('Foo3', file=f)

Какой бы способ вы ни выбрали, я бы предложил использовать with, поскольку он делает код намного легче читать.

Обновление. Это различие в производительности объясняется тем, что write сильно буферизируется и возвращается до того, как фактически произойдет запись на диск (см. этот ответ), тогда как print (возможно) использует буферизацию строк. Простым испытанием для этого было бы также проверить эффективность для длинных записей, где недостатки (с точки зрения скорости) для буферизации строк были бы менее выраженными.

start = start = time.time()
long_line = 'This is a speed test' * 100
with open("test.txt", 'w') as f:
    for i in range(1000000):
        # print(long_line, file=f)
        # f.write(long_line + '\n')
end = time.time()

print(end - start, "s")

Теперь разница в производительности становится гораздо менее выраженной, со средним временем 2,20 для write и 3.10s для print. Если вам нужно объединить кучу строк, чтобы получить эту производительность линии loooong, пострадают, поэтому варианты использования, где print будут более эффективными, немного редки.

Ответ 8

Начиная с 3.5 вы также можете использовать pathlib для этой цели:

Path.write_text (данные, кодировка = нет, ошибки = нет)

Откройте указанный файл в текстовом режиме, запишите в него данные и закройте файл:

import pathlib

pathlib.Path('textfile.txt').write_text('content')

Ответ 9

Когда вы сказали "Линия", это означает некоторые сериализованные символы, которые заканчиваются символами "\n" . Строка должна быть последней в какой-то момент, поэтому мы должны рассмотреть "\n" в конце каждой строки. Вот решение:

with open('YOURFILE.txt', 'a') as the_file:
    the_file.write('Hello')

в режиме добавления после каждого перехода курсора в новую строку, если вы хотите использовать режим "w", вы должны добавить символы "\n" в конце функции write():

the_file.write('Hello'+'\n')

Ответ 10

Можно также использовать модуль io как в:

import io
my_string = "hi there"

with io.open("output_file.txt", mode='w', encoding='utf-8') as f:
    f.write(my_string)

Ответ 11

Вы также можете попробовать filewriter

pip install filewriter

from filewriter import Writer

Writer(filename='my_file', ext='txt') << ["row 1 hi there", "row 2"]

Пишет в my_file.txt

Принимает итерируемый или объект с поддержкой __str__.

Ответ 12

Когда мне нужно много писать новых строк, я определяю лямбду, которая использует функцию print:

out = open(file_name, 'w')
fwl = lambda *x, **y: print(*x, **y, file=out) # FileWriteLine
fwl('Hi')

Преимущество этого подхода состоит в том, что он может использовать все функции, доступные в функции print.

Обновление: как упомянул Георгий в разделе комментариев, можно улучшить эту идею с помощью partial функции:

from functools import partial
fwl = partial(print, file=out)

ИМХО, это более функциональный и менее загадочный подход.