P3 init und Text in Binär und in Blöcke unterteilt

This commit is contained in:
2025-06-25 16:37:06 +02:00
parent ca8e8e9621
commit 0fbfe58fbb
4 changed files with 390 additions and 7 deletions

234
P2/P2 Hazinedar.py Normal file
View File

@@ -0,0 +1,234 @@
import matplotlib.pyplot as plt
import numpy as np
# Linear Feedback Shift Register
class LFSR:
def __init__(self, poly):
# LSB -> MSB
self.g = []
self.reg = []
'''
poly = str(n, n-1, ..., 0) => g = [0, ..., n-1]
0, 1, ..., -1
[-1:0:-1] = von(inkl.):bis(exkl.):Schritt => [Ende:Anfang[
'''
for ziffer in poly[-1:0:-1]:
self.reg.append(0)
self.g.append(int(ziffer))
def get_reg_as_string(self):
reg_string = ""
for i in self.reg:
reg_string += str(i) # LSB -> MSB
return reg_string
def shift(self, s_i):
reg_old = self.reg.copy() # alter Zustand, um überschreibungen zu vermeiden
feedback = reg_old[-1] ^ int(s_i)
for i, value in enumerate(self.g):
if i == 0:
self.reg[i] = feedback
else:
if value == 1:
self.reg[i] = reg_old[i - 1] ^ feedback
else:
self.reg[i] = reg_old[i - 1]
def CRC_Parity(s, g):
schiebe_reg = LFSR(g)
# LSB -> MSB => MSB -> LSB
for s_i in s[::-1]:
schiebe_reg.shift(s_i)
return schiebe_reg.get_reg_as_string()
def channel_bsc(p, n):
errors = ""
for i in range(n):
errors += "1" if np.random.random() < p else "0"
return errors
def send_channel(p, codeword, error_pattern):
received = ""
for j in range(len(codeword)):
bit1 = int(codeword[j])
bit2 = int(error_pattern[j])
received += str(bit1 ^ bit2)
return received
def p_k_Fehler(p):
# P_k = (nCk) * p^k * (1-p)^(n-k)
n = 1000
p_k = []
k_values = list(range(1, n + 1))
for k in k_values:
nCk = 1
for i in range(1, k + 1, 1):
nCk = nCk * ((n + 1 - i) / i)
# p_k = (nCk) * p^k * (1-p)^(n-k)
p_k.append(nCk * pow(p, k) * pow((1 - p), (n - k)))
plt.figure(figsize=(12, 8))
plt.plot(k_values, p_k) # plot(x,y)
# Achsenbeschriftung
plt.xlabel('k (Anzahl Fehler)', fontsize=12)
plt.ylabel('p_k', fontsize=12)
plt.title(f'Fehlerwahrscheinlichkeiten BSC Kanal (p={p}, n={n})', fontsize=14)
# Grid
plt.grid(True, alpha=0.3)
# Zeige Plot
plt.tight_layout() # Besseres Layout
plt.show()
def optimal_blocksize(p, word, poly):
crc_bits = len(poly) - 1
n = len(word)
best_datasize = float('inf')
best_blocksize = 0
for i in range(10):
block_size_i = 2 ** i
if block_size_i < n:
blocks = n / block_size_i
codeword_size = block_size_i + crc_bits
p_succesful = (1 - p) ** codeword_size
block_avrg_reps = 1 / p_succesful
block_avrg_datasize = codeword_size * block_avrg_reps
total_avrg_datasize = block_avrg_datasize * blocks
if total_avrg_datasize < best_datasize:
best_datasize = total_avrg_datasize
best_blocksize = block_size_i
return best_blocksize
def generate_random_binary(n):
bin_string = ""
for i in range(n):
bin_string += "1" if np.random.random() < 0.5 else "0"
return bin_string
def split_into_blocks(word, block_size):
blocks = []
for i in range(0, len(word), block_size):
block = word[i:i + block_size]
blocks.append(block)
return blocks
def main():
p = 0.1
n = 1000
detected_blocks = 0
repeats = 0
total_errors = 0
total_transmited_data = 0
# LSB -> MSB
# s = "110011101100101"
word = generate_random_binary(n)
# MSB -> LSB
poly = "100101"
blocksize = optimal_blocksize(p, word, poly)
blocks = split_into_blocks(word, blocksize)
p_k_Fehler(p)
for i, block in enumerate(blocks):
# CRC-Codierung
crc_bits = CRC_Parity(block, poly)
codeword = crc_bits + block
# BSC-Kanal
error_pattern = channel_bsc(p, len(codeword))
received = send_channel(p, codeword, error_pattern)
# Fehlerprüfung
check = CRC_Parity(received, poly)
print(f"==========BLOCK {i + 1}==========")
print(f" Codewort: {codeword}")
print(f" Empfangen: {received}")
detected_blocks += 1 if "1" in check else 0
total_transmited_data += len(codeword)
repeats += 1
if "1" in check:
print(" ❌ Fehler ")
total_errors += error_pattern.count("1")
else:
print(" ✅ Erfolgreich")
'''
Version in der fehlerhafte Übertragungen so lange wiederholt werden, bis sie fehlerfrei sind
'''
'''
while "1" in check:
print(" ❌ Fehler ")
total_errors += error_pattern.count("1")
# erneute Übertragung
repeats += 1
total_transmited_data += len(codeword)
error_pattern = channel_bsc(p, len(codeword))
received = send_channel(p, codeword, error_pattern)
check = CRC_Parity(received, poly)
print(f" Empfangen: {received}")
print(" ✅ Erfolgreich \n")
'''
# Ende
print("============ ERGEBNISSE ============")
print(f"ursprüngliche Datenmenge: {n} Bits")
print(f" p: {p * 100} %")
print(f" generator Polynom: {poly}")
print(f" Blockgröße: {blocksize}")
print(f" Blockanzahl: {len(blocks)}")
print(f" übertragene Datenmenge: {total_transmited_data} Bit")
print(
f" fehlerfreie Blöcke: {len(blocks) - detected_blocks} = {((len(blocks) - detected_blocks) / len(blocks) * 100):.2f} %")
print(f" Wiederholungen: {repeats}, ca. {(repeats / len(blocks)):.1f} p.Bl.")
print(f" fehlerhafte Bits: {total_errors} Bit = {(total_errors / total_transmited_data * 100):.2f}%")
if __name__ == '__main__':
main()

View File

@@ -181,24 +181,28 @@ def main():
print(f"==========BLOCK {i + 1}==========")
print(f" Codewort: {codeword}")
print(f" Fehlerwort: {error_pattern}")
print(f" Empfangen: {received}")
detected_blocks += 1 if "1" in check else 0
total_transmited_data += len(codeword)
repeats += 1
'''
if "1" in check:
print(" ❌ Fehler ")
total_errors += error_pattern.count("1")
print(" ❌ Fehler ")
total_errors += error_pattern.count("1")
else:
print(" ✅ Erfolgreich")
print(" ✅ Erfolgreich")
'''
'''
Version in der fehlerhafte Übertragungen so lange wiederholt werden, bis sie fehlerfrei sind
'''
'''
while "1" in check:
print(" ❌ Fehler ")
total_errors += error_pattern.count("1")
@@ -213,7 +217,7 @@ def main():
print(" ✅ Erfolgreich \n")
'''
# Ende
@@ -224,8 +228,7 @@ def main():
print(f" Blockgröße: {blocksize}")
print(f" Blockanzahl: {len(blocks)}")
print(f" übertragene Datenmenge: {total_transmited_data} Bit")
print(
f" fehlerfreie Blöcke: {len(blocks) - detected_blocks} = {((len(blocks) - detected_blocks) / len(blocks) * 100):.2f} %")
print(f" fehlerfreie Blöcke: {len(blocks) - detected_blocks} = {((len(blocks) - detected_blocks) / len(blocks) * 100):.2f} %")
print(f" Wiederholungen: {repeats}, ca. {(repeats / len(blocks)):.1f} p.Bl.")
print(f" fehlerhafte Bits: {total_errors} Bit = {(total_errors / total_transmited_data * 100):.2f}%")

145
P3/main.py Normal file
View File

@@ -0,0 +1,145 @@
# --- Aus P1 ---
import math
ELEMENTS = []
INTERVALLS = []
N = 32 # länge eines Codeworts
class Element:
id = ""
count = 0
p_x_i = 0
I_x_i = 0
bin = ""
def __init__(self, id):
self.id = id
self.count = 1
def find_element(list, target_it):
for element in list:
if element.id == target_it:
return element
return None
def read_text_file():
path = './text.txt'
with open(path, 'r', encoding='utf-8') as file:
content = file.read()
return content
def Z_statistik(message):
# Ergebnisse mit https://de.planetcalc.com/2476/ prüfbar
# message = read_text_file()
m = len(message)
elements = []
for char in message:
entry = find_element(elements, char)
if entry is not None:
entry.count += 1
else:
elements.append(Element(char))
return calculate(elements, m, message)
def calculate(elements, m, message):
h = 0
for element in elements:
element.p_x_i = element.count / m
element.I_x_i = -1 * math.log2(element.p_x_i)
h += element.p_x_i * element.I_x_i
# Ausgabe
elements.sort(key=lambda element: element.count, reverse=True)
"""for element in elements:
print(f"{element.count:3.0f} | {element.p_x_i:10.7f} | {element.I_x_i:10.7f} | »{element.id}«")
print("Entropie = " + h.__str__() + "\n\n")"""
return elements
# --- Aus P1 ---
def charToBin():
global ELEMENTS
for element in ELEMENTS:
element.bin = format(ord(element.id), 'b')
def calcBitCount(block):
p = 1
for char in block:
element = find_element(ELEMENTS, char)
p *= element.p_x_i
N = round(-math.log(p), 0)
return N
def calcIntervalls():
global INTERVALLS
current_limit = 0
for element in ELEMENTS:
new_limit = current_limit + element.p_x_i
current_limit = new_limit
INTERVALLS.append(new_limit)
def createBlocks(message):
blocks = []
block = []
for char in message:
if len(block) == 0:
block.append(char)
continue
if calcBitCount(block) <= N:
block.append(char)
else:
blocks.append(block)
block = []
return blocks
def createCodeWord(block):
intervall = []
for char in block:
# zeichen für zeichen durch das aktuelle arbeitsintervall wandern und nach jedem Schritt eine Neuberechnung im neuen Teilintervall vornehmen
def AC_Encoder():
global ELEMENTS
global INTERVALLS
message = read_text_file()
l = len(message)
l_bin = l * 8
ELEMENTS = Z_statistik(message)
charToBin()
calcIntervalls()
blocks = createBlocks(message)
print(blocks)
AC_Encoder()

1
P3/text.txt Normal file
View File

@@ -0,0 +1 @@
Die Geschichte Korsikas im Altertum ist, obwohl die Insel nie als wohlhabend galt, von Kämpfen um die Vorherrschaft durch fremde Mächte geprägt. Eine erste Besiedlung der Insel ist für das 8. Jahrtausend v. Chr. nachgewiesen. Die Nachfolger der neolithischen Kulturen konnten ihre Traditionen zwar noch bis weit in die römische Herrschaftszeit aufrechterhalten, doch interessierten sich bereits vor den Römern Etrusker, Phönizier und Karthager, Griechen und nach ihnen Vandalen, Byzantiner und Sarazenen für die Insel. Für die größeren Reiche hatte Korsika vor allem als Stützpunkt im Mittelmeer strategische Bedeutung. Im 6. Jahrhundert v. Chr. begann unter dem Einfluss der Karthager eine Verstädterung auf der Insel. Konnte der Versuch einer griechischen Kolonisation noch im selben Jahrhundert mit dem zentralen Element der Gründung der Stadt Alalia zunächst von den Karthagern verhindert werden, übernahmen zu Beginn des folgenden Jahrhundert die Etrusker die Kolonialisierung. Im 4. Jahrhundert v. Chr. gab es einen letzten griechischen Versuch, die Insel zu gräzisieren, doch scheiterten sie erneut. Von nun an rückte die Insel immer mehr ins Blickfeld Roms, das schon gegen Ende des 5. Jahrhunderts v. Chr. mit der Gründung einer eigenen Kolonie zunächst gescheitert war. Dennoch geriet Korsika immer mehr in die römische Einflusssphäre und ab 259 v. Chr. wurde sie schließlich erobert. Nach Sicilia wurde Korsika im Verbund mit Sardinien die zweite römische Provinz, Sardinia et Corsica. Einzig während der Bürgerkriege passierten auf Korsika einige Dinge, die auch von überregionaler Bedeutung waren. So war die Insel längere Zeit im Machtbereich und eine Operationsbasis von Sextus Pompeius. Mit dem Beginn der Kaiserzeit wurde Sardinia et Corsica eine senatorische Provinz, was ihre relative Bedeutungslosigkeit aufzeigt. Keine Legionen waren hier stationiert, äußere Feinde drohten nicht und auch die Versorgung der Stadt Rom hing nicht von der Insel ab. Selbst die Reformen des Diokletian gegen Ende des 3. Jahrhunderts änderten nichts am korsischen Status. Erst im frühen 5. Jahrhundert eroberte mit den Westgoten erstmals eine fremde Macht seit mehr als 650 Jahren die Insel. Nachdem auch die Vandalen und Ostgoten kurzzeitig die Insel übernommen hatte, konnten in den 530er Jahren die Oströmer (Byzantiner) sie zurückgewinnen. 40 Jahre später besetzten die Langobarden strategisch wichtige Küstengebiete, das Innere blieb jedoch byzantinisch. Mittlerweile hatte sich die Kirche als der eigentliche Rückhalt der Bevölkerung etabliert. Bis weit ins Frühmittelalter war Korsika nun Spielball äußerer Mächte.