Я устанавливаю скрипт, который берет изображения .jpg из папки с именем {number} .jpg и сравнивает это число, умноженное на частоту кадров, с диапазоном, заданным в файле csv. Затем jpg копируется в ту же папку, что и файл csv, содержащий диапазон, в который он помещается.
Таким образом, данные CSV выглядят так:
477.01645354635303,1087.1628371628808
1191.5980219780615,1777.622457542435
1915.5956043956126,2525.6515684316387
2687.7457042956867,3299.803336663285
3429.317892107908,4053.6603896103848
4209.835924075932,4809.700129870082
(файлов много, но это один полный пример)
Каждое число будет сравниваться с каждым из этих диапазонов и помещаться в соответствующую папку. Если я просто распечатываю целевой файл и место назначения, все работает нормально, и результаты ожидаются. Но если я попытаюсь использовать любую из функций копирования shutil (copy, copyfile, copy2), цикл будет прерван.
Структура файла выглядит так:
Данные
| -Дрессировка
| - КОМПРЕССИЯ (СЛР)
| --- СЖАТИЕ (CPR) .csv
| --- Где данные изображения будут идти
| --Больше папок ..
| -Validation
| --Так как Тренинг
| -Тест
| --Так как Тренинг
Это Python 3. Я запускаю VS Code на машине с Ubuntu (Pop! OS). Я пробовал каждую из shutil
функций копирования, которые подходят для этого случая (copy
, copy2
, copyfile
). Я пробовал копировать в разные папки, и это работает. Если я копирую файлы в родительскую папку (т. Е. Обучение в вышеупомянутой иерархии), а не в подкаталоги, он работает нормально. Однако они нужны мне в подкаталоге для целей маркировки.
for cur in file_list:
with open(cur, 'r') as img:
filename = ntpath.basename(cur)
frame_num = int(filename[:-4]) # get number from filename
frame_num = (frame_num - 1) * (30000./1001.) # it's one second from each frame in a video
training = get_folders(train_path)
for folder in training:
train_csvfile = get_files(train_path + folder)
if len(train_csvfile) > 0:
with open(train_csvfile[0], 'r', encoding='latin-1', newline='') as source:
train_reader = csv.reader(source, delimiter = ',')
for trdata in train_reader:
if frame_num > float(trdata[0]) and frame_num < float(trdata[1]):
tr_path = os.path.join(train_path + folder, ntpath.basename(cur))
copy2(cur,tr_path)
print('Copied {} to training folder {}.'.format(filename, tr_path))
Код для получения файлов и папок:
def get_folders(a_dir):
return [name for name in os.listdir(a_dir)
if os.path.isdir(os.path.join(a_dir, name))]
def get_files(a_dir):
a_dir = Path(a_dir)
return [f for f in a_dir.glob('**/*') if f.is_file()]
file_list = get_files('/media/username/Seagate Expansion Drive/EXP 3/S1 C2/frames')
Полный вывод:
Copied 000017.jpg to training folder /home/username/Downloads/Event Data CSV/Data/Training/CPR (COMPRESSION)/000017.jpg.
Copied 000018.jpg to training folder /home/username/Downloads/Event Data CSV/Data/Training/CPR (COMPRESSION)/000018.jpg.
Copied 000019.jpg to training folder /home/username/Downloads/Event Data CSV/Data/Training/CPR (COMPRESSION)/000019.jpg.
Copied 000021.jpg to training folder /home/username/Downloads/Event Data CSV/Data/Training/CPR (COMPRESSION)/000021.jpg.
Traceback (most recent call last):
File "tfinput.py", line 39, in <module>
for trdata in train_reader:
_csv.Error: line contains NULL byte
Файлы правильно скопированы, как сказано (но ТОЛЬКО эти четыре из сотен)
Файлы csv в этом сценарии не изменяются вообще. Скрипт проходит через четыре изображения и вылетает с вышеуказанной ошибкой. Он правильно размещает эти четыре изображения. Если я попытаюсь снова запустить сценарий без регенерации данных, он сразу же вылетает. Однако, если я не использую функцию копирования, все работает нормально, и все правильные каталоги ввода и вывода приведены в моих инструкциях печати. Сценарий также может быть перезапущен без регенерации, когда нет оператора копирования. Это заставляет меня думать, что должна быть какая-то проблема с перезаписью, но так как я на самом деле не редактирую файлы csv, я не могу это указать.
Я ожидаю, что он должен просто скопировать файлы из источника в место назначения.
РЕДАКТИРОВАТЬ: Я пошел вперед и распечатал весь файл, на котором он застрял. И кажется, что он читает первую строку, а затем вылетает. Я проверил это на другом файле и подтвердил, что он просто копирует файлы в первом диапазоне, а затем вылетает
РЕДАКТИРОВАТЬ 2: Я смог заставить это работать с помощью блока try-except
в блоке, начиная с for trdata in train_reader:
, однако он пропустил много записей
РЕДАКТИРОВАТЬ 3: Для любопытных я никогда не выяснял проблему, хотя подозреваю, что это была проблема перезаписи, так как проверка значений NULL без оператора copy ничего не дала. Я реорганизовал код, в котором я сначала создал текстовый файл с именем папки и имени файла, а затем прочитал этот файл и скопировал файлы. Это сработало идеально.
Спасибо за любую помощь !!