zusammenfügen 30.1.

This commit is contained in:
2026-01-30 18:41:46 +01:00
parent 1561eb242e
commit d069b7ca81
10 changed files with 65708 additions and 35899 deletions

View File

@@ -2,6 +2,7 @@ import numpy as np
import plotly.graph_objects as go
from scipy.stats import f
import pandas as pd
import Berechnungen
class Genauigkeitsmaße:
@@ -196,6 +197,159 @@ class Genauigkeitsmaße:
@staticmethod
def konfidenzellipsoid(Qxx, s0_apost, unbekannten_liste, R, alpha, skala="f", return_2d_schnitte=True):
Qxx = np.asarray(Qxx, float)
namen_str = [str(sym) for sym in unbekannten_liste]
punkt_ids = sorted({n[1:] for n in namen_str if n and n[0].upper() in ("X", "Y", "Z")})
# Skalierungsfaktor für Konfidenzbereich
if skala.lower() == "f":
k2_3d = f.ppf(1.0 - alpha, df=3)
elif skala.lower() == "f":
k2_3d = 3.0 * f.ppf(1.0 - alpha, dfn=3, dfd=R)
else:
raise ValueError("skala muss 'chi2' oder 'f' sein.")
daten = []
for pid in punkt_ids:
try:
idx_x = next(i for i, n in enumerate(namen_str) if n.upper() == f"X{pid}".upper())
idx_y = next(i for i, n in enumerate(namen_str) if n.upper() == f"Y{pid}".upper())
idx_z = next(i for i, n in enumerate(namen_str) if n.upper() == f"Z{pid}".upper())
except StopIteration:
continue
# 3x3-Block aus Qxx ziehen
I = [idx_x, idx_y, idx_z]
Qp = Qxx[np.ix_(I, I)]
# Kovarianzmatrix (Sigma) des Punkts
Sigma = (s0_apost ** 2) * Qp
# Standardabweichungen
sx = float(np.sqrt(Sigma[0, 0]))
sy = float(np.sqrt(Sigma[1, 1]))
sz = float(np.sqrt(Sigma[2, 2]))
# Kovarianzen
sxy = float(Sigma[0, 1])
sxz = float(Sigma[0, 2])
syz = float(Sigma[1, 2])
# Eigenzerlegung (symmetrisch -> eigh)
evals, evecs = np.linalg.eigh(Sigma)
order = np.argsort(evals)[::-1]
evals = evals[order]
evecs = evecs[:, order]
# Numerische Sicherheit: negative Mini-Eigenwerte durch Rundung abklemmen
evals = np.clip(evals, 0.0, None)
# Halbachsen des Konfidenzellipsoids:
A, B, C = (np.sqrt(evals * k2_3d)).tolist()
row = {
"Punkt": pid,
"σx": sx, "σy": sy, "σz": sz,
"σxy": sxy, "σxz": sxz, "σyz": syz,
"A_K": float(A), "B_K": float(B), "C_K": float(C),
# Orientierung als Spaltenvektoren (Eigenvektoren)
"evec_1": evecs[:, 0].tolist(),
"evec_2": evecs[:, 1].tolist(),
"evec_3": evecs[:, 2].tolist(),
"skala_k2": float(k2_3d),
"skala_typ": skala.lower()
}
# Optional: 2D-Schnitte (XY, XZ, YZ) als Ellipsenparameter
if return_2d_schnitte:
row.update(Genauigkeitsmaße.ellipsen_schnitt_2d(Sigma, alpha, R, skala))
daten.append(row)
return pd.DataFrame(daten)
@staticmethod
def ellipsen_schnitt_2d(Sigma3, alpha, R, skala):
def ellipse_from_2x2(S2):
# Skalierung für 2D
if skala.lower() == "f":
k2 = f.ppf(1.0 - alpha, df=2)
else:
k2 = 2.0 * f.ppf(1.0 - alpha, dfn=2, dfd=R)
evals, evecs = np.linalg.eigh(S2)
order = np.argsort(evals)[::-1]
evals = np.clip(evals[order], 0.0, None)
evecs = evecs[:, order]
a, b = np.sqrt(evals * k2)
# Winkel der Hauptachse (zu a) in der Ebene: atan2(vy, vx)
vx, vy = evecs[0, 0], evecs[1, 0]
theta_rad = np.arctan2(vy, vx)
theta_gon = float(theta_rad * (200.0 / np.pi)) % 200.0
return float(a), float(b), theta_gon
# Submatrizen
S_xy = Sigma3[np.ix_([0, 1], [0, 1])]
S_xz = Sigma3[np.ix_([0, 2], [0, 2])]
S_yz = Sigma3[np.ix_([1, 2], [1, 2])]
axy, bxy, txy = ellipse_from_2x2(S_xy)
axz, bxz, txz = ellipse_from_2x2(S_xz)
ayz, byz, tyz = ellipse_from_2x2(S_yz)
return {
"aXY": axy, "bXY": bxy, "θXY [gon]": txy,
"aXZ": axz, "bXZ": bxz, "θXZ [gon]": txz,
"aYZ": ayz, "bYZ": byz, "θYZ [gon]": tyz,
}
@staticmethod
def transform_q_with_your_functions(q_xyz, B, L):
# East
r11 = Berechnungen.E(L, 1, 0)
r12 = Berechnungen.E(L, 0, 1)
r13 = 0
# North
r21 = Berechnungen.N(B, L, 1, 0, 0)
r22 = Berechnungen.N(B, L, 0, 1, 0)
r23 = Berechnungen.N(B, L, 0, 0, 1)
# Up
r31 = Berechnungen.U(B, L, 1, 0, 0)
r32 = Berechnungen.U(B, L, 0, 1, 0)
r33 = Berechnungen.U(B, L, 0, 0, 1)
R = np.array([
[r11, r12, r13],
[r21, r22, r23],
[r31, r32, r33]
])
q_enu = R @ q_xyz @ R.T
return q_enu
def plot_netz_komplett_final(x_vektor, unbekannten_labels, beobachtungs_labels, Qxx, sigma0_apost,
k_faktor=2.447, v_faktor=1000):
"""