Testauswertung zusammengeführt und in den Testablauf integriert
In excel_processing habe ich nur den Funktionsaufruf der Evaluation hinzugefügt, die evaluation enthält die Funktionalitäten aus dem Testauswertung-Ordner
This commit is contained in:
parent
7c2c8f1b4d
commit
db476fbce2
151
code/excel_evaluation.py
Normal file
151
code/excel_evaluation.py
Normal file
@ -0,0 +1,151 @@
|
||||
import openpyxl
|
||||
|
||||
def excel_row_to_string(file_path):
|
||||
# Öffne die Excel-Datei
|
||||
workbook = openpyxl.load_workbook(file_path)
|
||||
|
||||
# Wähle das Arbeitsblatt aus
|
||||
sheet = workbook['Sheet1']
|
||||
|
||||
# Erhalte die angegebene Zeile als Liste von Zellen
|
||||
row_values = [cell.value for cell in sheet[2]]
|
||||
|
||||
# Ergebnisse werden ab Spalte 5 eingetragen
|
||||
selected_columns = list(range(4, len(row_values)))
|
||||
|
||||
# Wähle nur die gewünschten Spalten aus
|
||||
selected_values = [row_values[col] for col in selected_columns]
|
||||
|
||||
# Schließe die Excel-Datei
|
||||
workbook.close()
|
||||
|
||||
# Konvertiere die Liste von Zellen in einen String
|
||||
row_string = ', '.join(str(value) for value in selected_values)
|
||||
|
||||
return row_string
|
||||
|
||||
def write_subdivided_string_to_excel(file_path, input_string):
|
||||
# Öffne die Excel-Datei
|
||||
workbook = openpyxl.load_workbook(file_path)
|
||||
|
||||
# Wähle das Arbeitsblatt aus
|
||||
sheet = workbook['Sheet1']
|
||||
|
||||
# Teile den String nach jedem Komma auf
|
||||
parts = input_string.split(',')
|
||||
|
||||
# Trage jeden Teil des Strings in eine neue Zeile ein
|
||||
for i, part in enumerate(parts, 1):
|
||||
|
||||
#Spalte 17 kann sich je nach Tabellenstruktur ändern!
|
||||
sheet.cell(row=2 + i - 1, column=17, value=part.strip()) # strip entfernt mögliche Leerzeichen
|
||||
|
||||
# Speichere die Änderungen
|
||||
workbook.save(file_path)
|
||||
|
||||
# Schließe die Excel-Datei
|
||||
workbook.close()
|
||||
|
||||
def read_columns(file_path):
|
||||
# Öffne die Excel-Datei
|
||||
workbook = openpyxl.load_workbook(file_path)
|
||||
|
||||
# Wähle das Arbeitsblatt aus
|
||||
sheet = workbook['Sheet1']
|
||||
|
||||
# Lese die Werte der beiden Spalten aus
|
||||
values_column1 = [cell.value for cell in sheet['O']][1:]
|
||||
values_column2 = [cell.value for cell in sheet['Q']][1:]
|
||||
|
||||
# Schließe die Excel-Datei
|
||||
workbook.close()
|
||||
|
||||
return values_column1, values_column2
|
||||
|
||||
def calculate_deviation(liste1, liste2):
|
||||
# Überprüfe, ob die Listen die gleiche Länge haben
|
||||
if len(liste1) != len(liste2):
|
||||
raise ValueError("Die Listen müssen die gleiche Länge haben")
|
||||
|
||||
# Berechne die prozentuale Abweichung zwischen den Werten
|
||||
deviations = [((abs(float(b) - float(a)) / float(a)) * 100) if float(a) != 0 else None for a, b in zip(liste1, liste2)]
|
||||
|
||||
return deviations
|
||||
|
||||
def write_string_to_excel(file_path, input_string, column):
|
||||
# Öffne die Excel-Datei
|
||||
workbook = openpyxl.load_workbook(file_path)
|
||||
|
||||
# Wähle das Arbeitsblatt aus
|
||||
sheet = workbook['Sheet1']
|
||||
|
||||
# Trage jeden Buchstaben des Strings in eine eigene Zeile ein
|
||||
for i, char in enumerate(input_string, 1):
|
||||
sheet.cell(row=2 + i - 1, column=column, value=char)
|
||||
|
||||
# Speichere die Änderungen
|
||||
workbook.save(file_path)
|
||||
|
||||
# Schließe die Excel-Datei
|
||||
workbook.close()
|
||||
|
||||
def copy_header(input_sheet, output_sheet):
|
||||
# Kopiere den Header manuell in das Ausgabe-Arbeitsblatt
|
||||
for row in input_sheet.iter_rows(min_row=1, max_row=1, values_only=True):
|
||||
output_sheet.append(row)
|
||||
|
||||
def sort_excel(input_file_path, output_file_path, ):
|
||||
# Öffne die Eingabe-Excel-Datei
|
||||
input_workbook = openpyxl.load_workbook(input_file_path)
|
||||
input_sheet = input_workbook['Sheet1']
|
||||
|
||||
# Erstelle eine neue Excel-Tabelle für die sortierten Zeilen
|
||||
output_workbook = openpyxl.Workbook()
|
||||
output_sheet = output_workbook.active
|
||||
|
||||
# Kopiere den Header ins Ausgabe-Arbeitsblatt
|
||||
copy_header(input_sheet, output_sheet)
|
||||
|
||||
# Lese die Daten-Zeilen aus der Tabelle
|
||||
data_rows = list(input_sheet.iter_rows(min_row=2, values_only=True))
|
||||
|
||||
# Sortiere die Daten-Zeilen nach dem Wert der angegebenen Spalte
|
||||
sorted_data_rows = sorted(data_rows, key=lambda x: x[18 - 1]) # -1, da Listenindizes bei 0 beginnen
|
||||
|
||||
# Schreibe die sortierten Daten-Zeilen in die neue Tabelle
|
||||
for row in sorted_data_rows:
|
||||
output_sheet.append(row)
|
||||
|
||||
# Speichere die Änderungen in der neuen Excel-Datei
|
||||
output_workbook.save(output_file_path)
|
||||
|
||||
# Schließe die Excel-Dateien
|
||||
input_workbook.close()
|
||||
output_workbook.close()
|
||||
|
||||
|
||||
#Sollten mehrere Testruns ausgewertet werden wollen, müssen die enthaltenen Funktionen umstrukturiert werden
|
||||
#Aktuell wird nur der Testrun in Zeile 1 ausgewertet
|
||||
#Eine Weitere Funktion, die zwei Tabellenzeilen tauscht, wäre der einfachste workaround
|
||||
def evaluation(testcases, testruns):
|
||||
|
||||
#liest die Ergebnisse des Testruns aus
|
||||
#bei mehreren Testruns muss diese Funktion angepasst werden!
|
||||
input_string = excel_row_to_string(testruns)
|
||||
|
||||
#schreibt die Berechneten Ergebnisse in die Testcases-Tabelle
|
||||
write_subdivided_string_to_excel(testcases, input_string)
|
||||
|
||||
#liest die gemessenen und die errechneten Werte aus den Testcases
|
||||
values_col1, values_col2 = read_columns(testcases)
|
||||
|
||||
#berechnet aus diesen Werten die prozentuale Abweichung
|
||||
deviations = calculate_deviation(values_col1, values_col2)
|
||||
|
||||
#Trägt die prozentualen Abweichungen in die Testcases-Tabelle
|
||||
#je nach Tabellenstruktur kann sich die 18 ändern!
|
||||
write_string_to_excel(testcases, deviations, 18)
|
||||
|
||||
#Gibt die eine Kopie der Testcases-Tabelle sortiert nach Genauigkeit aus
|
||||
sort_excel(testcases, 'Testcases_nach_Genauigkeit.xlsx')
|
||||
|
@ -1,132 +1,139 @@
|
||||
"""
|
||||
Abhängigkeiten:
|
||||
- pyramids (für den Aufbau der Bildpyramiden)
|
||||
- heartrate (zur Berechnung der Herzfrequenz)
|
||||
- preprocessing (für die Video-Vorverarbeitung)
|
||||
- eulerian (für die Euler'sche Video-Magnifikation)
|
||||
- tkinter und constants (für die GUI und Konstantenverwaltung)
|
||||
|
||||
Autor: Roberto Gelsinger
|
||||
Datum: 07.12.2023
|
||||
Version: Modulversion
|
||||
"""
|
||||
|
||||
import pyramids
|
||||
import heartrate
|
||||
import facedetection
|
||||
import eulerian
|
||||
from constants import freq_max, freq_min
|
||||
import pandas as pd
|
||||
from excel_update import color_cells_based_on_deviation
|
||||
|
||||
|
||||
def process_video_for_excel(selected_video_name):
|
||||
"""
|
||||
Verarbeitet ein ausgewähltes Video, um die Herzfrequenz der abgebildeten Person zu ermitteln.
|
||||
|
||||
Dieser Prozess umfasst die Vorverarbeitung des Videos, den Aufbau einer Laplace-Pyramide,
|
||||
die Anwendung von FFT-Filterung und Euler'scher Magnifikation, und schließlich die Berechnung
|
||||
der Herzfrequenz aus den Video-Daten.
|
||||
|
||||
Args:
|
||||
selected_video_name (str): Der Name des zu verarbeitenden Videos.
|
||||
|
||||
Returns:
|
||||
None: Die Funktion gibt direkt die berechnete Herzfrequenz auf der Konsole aus.
|
||||
"""
|
||||
|
||||
|
||||
|
||||
print("Reading + preprocessing video...")
|
||||
video_frames, frame_ct, fps = facedetection.read_video("videos/"+selected_video_name)
|
||||
|
||||
|
||||
print("Building Laplacian video pyramid...")
|
||||
lap_video = pyramids.build_video_pyramid(video_frames)
|
||||
|
||||
|
||||
|
||||
for i, video in enumerate(lap_video):
|
||||
if i == 0 or i == len(lap_video)-1:
|
||||
continue
|
||||
|
||||
print("Running FFT and Eulerian magnification...")
|
||||
result, fft, frequencies = eulerian.fft_filter(video, freq_min, freq_max, fps)
|
||||
lap_video[i] += result
|
||||
|
||||
|
||||
print("Calculating heart rate...")
|
||||
heart_rate = heartrate.find_heart_rate(fft, frequencies, freq_min, freq_max)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
print("Heart rate: ", heart_rate*0.7, "bpm")
|
||||
return heart_rate *0.7
|
||||
|
||||
|
||||
|
||||
def process_all_videos_and_save_results(testcase_excel_file_path, testruns_excel_file_path, code_version, kommentar):
|
||||
|
||||
try:
|
||||
df_testruns = pd.read_excel(testruns_excel_file_path)
|
||||
except FileNotFoundError:
|
||||
df_testruns = pd.DataFrame()
|
||||
|
||||
|
||||
df_testcases = pd.read_excel(testcase_excel_file_path)
|
||||
|
||||
existing_testcases = [col for col in df_testruns.columns if col.startswith('Testcase_')]
|
||||
|
||||
new_testcases = [f'Testcase_{tc}' for tc in df_testcases['Testcase'] if f'Testcase_{tc}' not in existing_testcases]
|
||||
|
||||
|
||||
if df_testruns.empty:
|
||||
df_testruns = pd.DataFrame(columns=['Testnummer', 'Codeversion', 'Kommentar', 'Abweichung'])
|
||||
|
||||
|
||||
for col in new_testcases:
|
||||
df_testruns[col] = None
|
||||
|
||||
|
||||
df_testruns.to_excel(testruns_excel_file_path, index=False)
|
||||
|
||||
if new_testcases:
|
||||
print(f"Folgende neue Testcases wurden hinzugefügt: {new_testcases}")
|
||||
else:
|
||||
print("Keine neuen Testcases zum Hinzufügen gefunden.")
|
||||
|
||||
next_testcase_index = len(df_testruns) + 1
|
||||
|
||||
|
||||
new_run = {
|
||||
'Testnummer': next_testcase_index,
|
||||
'Codeversion': code_version,
|
||||
'Kommentar': kommentar,
|
||||
'Abweichung': 'Wert_für_Abweichung'
|
||||
}
|
||||
|
||||
|
||||
for index, row in df_testcases.iterrows():
|
||||
video_name = row['VideoName']
|
||||
heart_rate = process_video_for_excel(video_name)
|
||||
|
||||
|
||||
testcase_column_name = f'Testcase_{row["Testcase"]}'
|
||||
new_run[testcase_column_name] = heart_rate
|
||||
|
||||
try:
|
||||
|
||||
df_testruns = df_testruns._append(new_run, ignore_index=True)
|
||||
except TypeError:
|
||||
pass
|
||||
|
||||
|
||||
df_testruns.to_excel(testruns_excel_file_path, index=False)
|
||||
|
||||
print("Testrun wurde verarbeitet und das Ergebnis in der Testruns-Excel-Datei gespeichert.")
|
||||
|
||||
color_cells_based_on_deviation(testruns_excel_file_path, testcase_excel_file_path)
|
||||
|
||||
print("Zellen gefärbt")
|
||||
"""
|
||||
Abhängigkeiten:
|
||||
- pyramids (für den Aufbau der Bildpyramiden)
|
||||
- heartrate (zur Berechnung der Herzfrequenz)
|
||||
- preprocessing (für die Video-Vorverarbeitung)
|
||||
- eulerian (für die Euler'sche Video-Magnifikation)
|
||||
- tkinter und constants (für die GUI und Konstantenverwaltung)
|
||||
|
||||
Autor: Roberto Gelsinger
|
||||
Datum: 07.12.2023
|
||||
Version: Modulversion
|
||||
"""
|
||||
|
||||
import pyramids
|
||||
import heartrate
|
||||
import facedetection
|
||||
import eulerian
|
||||
from constants import freq_max, freq_min
|
||||
import pandas as pd
|
||||
from excel_update import color_cells_based_on_deviation
|
||||
from excel_evaluation import evaluation
|
||||
|
||||
|
||||
def process_video_for_excel(selected_video_name):
|
||||
"""
|
||||
Verarbeitet ein ausgewähltes Video, um die Herzfrequenz der abgebildeten Person zu ermitteln.
|
||||
|
||||
Dieser Prozess umfasst die Vorverarbeitung des Videos, den Aufbau einer Laplace-Pyramide,
|
||||
die Anwendung von FFT-Filterung und Euler'scher Magnifikation, und schließlich die Berechnung
|
||||
der Herzfrequenz aus den Video-Daten.
|
||||
|
||||
Args:
|
||||
selected_video_name (str): Der Name des zu verarbeitenden Videos.
|
||||
|
||||
Returns:
|
||||
None: Die Funktion gibt direkt die berechnete Herzfrequenz auf der Konsole aus.
|
||||
"""
|
||||
|
||||
|
||||
|
||||
print("Reading + preprocessing video...")
|
||||
video_frames, frame_ct, fps = facedetection.read_video("videos/"+selected_video_name)
|
||||
|
||||
print(len(video_frames))
|
||||
|
||||
print("Building Laplacian video pyramid...")
|
||||
lap_video = pyramids.build_video_pyramid(video_frames)
|
||||
|
||||
print(len(lap_video))
|
||||
|
||||
for i, video in enumerate(lap_video):
|
||||
print("test")
|
||||
if i == 0 or i == len(lap_video)-1:
|
||||
continue
|
||||
|
||||
print("Running FFT and Eulerian magnification...")
|
||||
result, fft, frequencies = eulerian.fft_filter(video, freq_min, freq_max, fps)
|
||||
lap_video[i] += result
|
||||
|
||||
|
||||
print("Calculating heart rate...")
|
||||
heart_rate = heartrate.find_heart_rate(fft, frequencies, freq_min, freq_max)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
print("Heart rate: ", heart_rate*0.7, "bpm")
|
||||
return heart_rate *0.7
|
||||
|
||||
|
||||
|
||||
def process_all_videos_and_save_results(testcase_excel_file_path, testruns_excel_file_path, code_version, kommentar):
|
||||
|
||||
try:
|
||||
df_testruns = pd.read_excel(testruns_excel_file_path)
|
||||
except FileNotFoundError:
|
||||
df_testruns = pd.DataFrame()
|
||||
|
||||
|
||||
df_testcases = pd.read_excel(testcase_excel_file_path)
|
||||
|
||||
existing_testcases = [col for col in df_testruns.columns if col.startswith('Testcase_')]
|
||||
|
||||
new_testcases = [f'Testcase_{tc}' for tc in df_testcases['Testcase'] if f'Testcase_{tc}' not in existing_testcases]
|
||||
|
||||
|
||||
if df_testruns.empty:
|
||||
df_testruns = pd.DataFrame(columns=['Testnummer', 'Codeversion', 'Kommentar', 'Abweichung'])
|
||||
|
||||
|
||||
for col in new_testcases:
|
||||
df_testruns[col] = None
|
||||
|
||||
|
||||
df_testruns.to_excel(testruns_excel_file_path, index=False)
|
||||
|
||||
if new_testcases:
|
||||
print(f"Folgende neue Testcases wurden hinzugefügt: {new_testcases}")
|
||||
else:
|
||||
print("Keine neuen Testcases zum Hinzufügen gefunden.")
|
||||
|
||||
next_testcase_index = len(df_testruns) + 1
|
||||
|
||||
|
||||
new_run = {
|
||||
'Testnummer': next_testcase_index,
|
||||
'Codeversion': code_version,
|
||||
'Kommentar': kommentar,
|
||||
'Abweichung': 'Wert_für_Abweichung'
|
||||
}
|
||||
|
||||
|
||||
for index, row in df_testcases.iterrows():
|
||||
video_name = row['VideoName']
|
||||
heart_rate = process_video_for_excel(video_name)
|
||||
|
||||
|
||||
testcase_column_name = f'Testcase_{row["Testcase"]}'
|
||||
new_run[testcase_column_name] = heart_rate
|
||||
|
||||
try:
|
||||
|
||||
df_testruns = df_testruns._append(new_run, ignore_index=True)
|
||||
except TypeError:
|
||||
pass
|
||||
|
||||
|
||||
df_testruns.to_excel(testruns_excel_file_path, index=False)
|
||||
|
||||
print("Testrun wurde verarbeitet und das Ergebnis in der Testruns-Excel-Datei gespeichert.")
|
||||
|
||||
color_cells_based_on_deviation(testruns_excel_file_path, testcase_excel_file_path)
|
||||
|
||||
print("Zellen gefärbt")
|
||||
|
||||
evaluation(testcase_excel_file_path, testruns_excel_file_path)
|
||||
|
||||
print("Testcases sortiert")
|
Loading…
x
Reference in New Issue
Block a user