Files
nosology-vault/vault_simple.py
2025-09-08 16:39:34 +05:00

130 lines
6.0 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import pandas as pd
import os
import glob
class vault():
def __init__(self):
"""Простой класс для работы с Excel файлами"""
pass
def file_filter(self, dir_name):
"""Алгоритм 1: Перебор файлов в директории"""
print(f"Ищем в директории: {dir_name}")
print(f"Полный путь: {os.path.abspath(dir_name)}")
if not os.path.exists(dir_name):
print(f"Директория {dir_name} не существует")
return []
# Показываем все файлы в директории
all_files = os.listdir(dir_name)
print(f"Все файлы в директории: {len(all_files)} файлов")
# Поиск всех xls и xlsx файлов
pattern_xlsx = os.path.join(dir_name, "*.xlsx")
pattern_xls = os.path.join(dir_name, "*.xls")
print(f"Паттерн поиска xlsx: {pattern_xlsx}")
print(f"Паттерн поиска xls: {pattern_xls}")
xlsx_files = glob.glob(pattern_xlsx)
xls_files = glob.glob(pattern_xls)
# Объединяем все Excel файлы
excel_files = xlsx_files + xls_files
# Исключаем временные файлы Excel (начинающиеся с ~$)
excel_files = [f for f in excel_files if not os.path.basename(f).startswith('~$')]
print(f"Найдено {len(excel_files)} Excel файлов:")
for file in excel_files:
print(f" - {os.path.basename(file)}")
return excel_files
def open_xlsx(self, file_name, header_rows=1, row_filter=None):
"""Алгоритм 2: Перебор строк документа с настраиваемой шапкой и фильтром"""
try:
# Пробуем разные движки для чтения файлов
if file_name.endswith('.xls'):
# Для старых файлов .xls используем xlrd
df = pd.read_excel(file_name, header=list(range(header_rows)), engine='xlrd')
else:
# Для .xlsx используем openpyxl
df = pd.read_excel(file_name, header=list(range(header_rows)), engine='openpyxl')
print(f"Файл {os.path.basename(file_name)}: загружено {len(df)} строк")
# Применяем пользовательский фильтр если он задан
if row_filter and callable(row_filter):
original_count = len(df)
df = df[df.apply(row_filter, axis=1)]
filtered_count = len(df)
print(f"После фильтрации: {filtered_count} строк (исключено {original_count - filtered_count})")
return df
except Exception as e:
print(f"Ошибка при открытии файла {file_name}: {e}")
# Пробуем альтернативный способ
try:
print(f"Пробуем альтернативный движок для {os.path.basename(file_name)}")
df = pd.read_excel(file_name, header=list(range(header_rows)), engine='calamine')
print(f"Успешно загружено {len(df)} строк альтернативным способом")
if row_filter and callable(row_filter):
original_count = len(df)
df = df[df.apply(row_filter, axis=1)]
filtered_count = len(df)
print(f"После фильтрации: {filtered_count} строк")
return df
except Exception as e2:
print(f"Альтернативный способ тоже не сработал: {e2}")
return pd.DataFrame()
def merge_files(self, dir_name, output_file="merged.xlsx", header_rows=1, row_filter=None):
"""Объединяет файлы с настройками шапки и фильтра"""
# Алгоритм 1: находим файлы
files = self.file_filter(dir_name)
if not files:
print("Файлы не найдены")
return
all_data = []
# Алгоритм 2: обрабатываем каждый файл
for file_path in files:
df = self.open_xlsx(file_path, header_rows, row_filter)
if not df.empty:
# Добавляем информацию об источнике
df['сточник'] = os.path.basename(file_path)
all_data.append(df)
if all_data:
# Объединяем все данные
result = pd.concat(all_data, ignore_index=True)
# Сохраняем результат
result.to_excel(output_file, index=False)
print(f"\nОбъединено {len(result)} строк в файл {output_file}")
else:
print("Нет данных для объединения")
# Примеры использования
if __name__ == "__main__":
vault_instance = vault()
print("\n=== Пример 3: С фильтром строк ===")
def my_filter(row):
# Исключаем строки где первый столбец пустой
return not pd.isna(row.iloc[0]) and row.iloc[0] != ""
# Ищем файлы в папке ПРИЕММ и сохраняем результат как merged.xlsx
# Попробуйте с разными вариантами имени папки:
vault_instance.merge_files(".\ПРИЕММ", "merged.xlsx", row_filter=my_filter)
# или
# vault_instance.merge_files(r"ПРИЕММ", "merged.xlsx", row_filter=my_filter)