Python 3: идиоматический способ удалить последний символ в файле - PullRequest
0 голосов
/ 03 февраля 2019

Есть ли идиоматический способ сделать это?Я только что обновился с Python 2 до Python 3, и я пытаюсь перенести свой скрипт, и должен сказать, что я не впечатлен.Из того, что я могу сказать, мой код получает

от этого

# Not allowed by Python 3 anymore without being in binary mode.
card_names_file.seek(-1, os.SEEK_END)
if card_names_file.read() == ',':
    card_names_file.truncate()

до этого

# Go to end of file just to get position index. lawl.
card_names_file.seek(0, os.SEEK_END)
# Create a temporary just to store said index. More lawl.
eof = card_names_file.tell()
# Index one from the back. ugh. w/e, that's fine.
card_names_file.seek(eof - 1, os.SEEK_SET)

# Oh wait, .read() will advance my pointer. Oh hey Python 3 doesn't let me
# use .peek() either. Fantastic. I'll have to read this...
if card_names_file.read() == ',':
    # Then go back to where I was by indexing from front AGAIN
    card_names_file.seek(eof - 1, os.SEEK_SET)
    # Then remove last character.
    card_names_file.truncate()

Это самый тупой код, который я почти когда-либо видели я потратил 2 с половиной часа, пытаясь удалить символ из конца файла, и это выглядит как хак.

Альтернатива заключается в том, что у меня есть код, который выглядит следующим образом

# open file
with open(file, a+)
    # do stuff

# open same file
with open(file, w+b)
    # do different stuff

Но я не могу заставить это работать.

1 Ответ

0 голосов
/ 03 февраля 2019

Базовый буфер действительно имеет метод peek(), который вы искали, поэтому:

f = open('FILE', 'a+')
f.seek(f.seek(0, os.SEEK_END) - 1)
# or with the same effect you can also:
os.lseek(f.fileno(), -1, os.SEEK_END)
# Actually in append mode we could just seek by -1 from where we are
# (cursor at the end after opening)
f.tell()  # just to see...
f.buffer.peek(1)
f.tell()  # ...still where we were

В качестве альтернативы, вы также можете использовать os.pread().Например:

os.pread(f.fileno(), 1, os.fstat(f.fileno()).st_size - 1)

Это не очень идиоматично, как при использовании доступа к файлам абстракции более высокого уровня, но я бы вызвал : "Хотя практичность превосходит чистоту."

...