[Python] Morsealphabet Übersetzer

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

Hey Leute,


ich programmiere momentan einen Code für Python um einen eingegebenen Text in Morsesprache zu übersetzen.

Bisher habe ich folgendes programmiert:

Code: Alles auswählen

import time

print("RaspberryMorse")
print("Senden über GPIO-17 und Empfangen über GPIO-18 bei RSBPI B+")
print("Senden über GPIO-22 und Empfangen über GPIO-23 bei RSBPI B")

time.sleep(5)

print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
print("                                 ")
text = raw_input("Dein-Text: ")
textln = len(text)
akt = 0
decodierttext = ""

def kurz(decodierttext):
    decodierttext = decodierttext,"."

def lang(decodierttext):
    decodierttext = decodierttext,"-"
    
def leer(decodierttext):
    decodierttext = decodierttext,"...----.."
    





while akt < textln:
    if akt == 0:
        akt+1
    else:
        
        
        if text[akt] == "A" or text[akt] == "a":
            time.sleep(0.3)
            kurz(decodierttext)
            lang(decodierttext)
        if text[akt] == "B" or text[akt] == "b":
            time.sleep(0.3)
            lang(decodierttext)
            kurz(decodierttext)
            kurz(decodierttext)
            kurz(decodierttext)
        if text[akt] == "C" or text[akt] == "c":
            time.sleep(0.3)
            lang(decodierttext)
            kurz(decodierttext)
            lang(decodierttext)
            kurz(decodierttext)
        if text[akt] == "D" or text[akt] == "d":
            time.sleep(0.3)
            lang(decodierttext)
            kurz(decodierttext)
            kurz(decodierttext)
        if text[akt] == "E" or text[akt] == "e":
            time.sleep(0.3)
            kurz(decodierttext)
        if text[akt] == "F" or text[akt] == "f":
            time.sleep(0.3)
            kurz(decodierttext)
            kurz(decodierttext)
            lang(decodierttext)
            kurz(decodierttext)
        if text[akt] == "G" or text[akt] == "g":
            time.sleep(0.3)
            lang(decodierttext)
            lang(decodierttext)
            kurz(decodierttext)
        if text[akt] == "H" or text[akt] == "h":
            time.sleep(0.3)
            kurz(decodierttext)
            kurz(decodierttext)
            kurz(decodierttext)
            kurz(decodierttext)
        if text[akt] == "I" or text[akt] == "i":
            time.sleep(0.3)
            kurz(decodierttext)
            kurz(decodierttext)
        if text[akt] == "J" or text[akt] == "j":
            time.sleep(0.3)
            kurz(decodierttext)
            lang(decodierttext)
            lang(decodierttext)
            lang(decodierttext)
    akt = akt + 1
print akt
print decodierttext


Immer wenn ich das eingebe kommt am ende beim Print bei akt die Buchstabenzahl raus wie lang der Text war.

Bei decodierttext kommt garnichts....


und das Programm wird beendet, was auch richtig ist


Why?? :?: :?: :?:


Danke im voraus für Hilfe


LG Jannis2711
Benutzeravatar
darktrym
User
Beiträge: 784
Registriert: Freitag 24. April 2009, 09:26

leer, lang, kurz mit Rückgabewerten versehen und diese auch mal decodiertext zuweisen.
Natürlich ist decodiertext auf Modulebene leer, wird ja nie gefüllt. Achja akt+1 macht wenig Sinn.
„gcc finds bugs in Linux, NetBSD finds bugs in gcc.“[Michael Dexter, Systems 2008]
Bitbucket, Github
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

Bin noch ziemlich neu und muss das für die schule machen, kannst du mir bitte einmal erklären wie das genau funktioniert?

LG Jannis2711
Benutzeravatar
pillmuncher
User
Beiträge: 1484
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

@jannis2711: Hast du deinen Code mal ausprobiert?

Code: Alles auswählen

>>> decodierttext = ""
>>> def kurz(decodierttext):
...     decodierttext = decodierttext,"."
...
>>> s = 'hallo'
>>> kurz(s)
>>> s
'hallo'
>>> decodierttext
''
Zuletzt geändert von pillmuncher am Freitag 9. Januar 2015, 15:14, insgesamt 1-mal geändert.
In specifications, Murphy's Law supersedes Ohm's.
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

ja aber er soll ja den Punkt hinzufügen
Benutzeravatar
pillmuncher
User
Beiträge: 1484
Registriert: Samstag 21. März 2009, 22:59
Wohnort: Pfaffenwinkel

Auch das Hinzufügen vom Punkt ist falsch:

Code: Alles auswählen

>>> decodierttext = decodierttext,"."
>>> decodierttext
('', '.')
Ich empfehle das Tutorial. Oder auf Deutsch.
In specifications, Murphy's Law supersedes Ohm's.
BlackJack

@jannis2711: In Zeile 68 bindest Du den Namen `dekodierttext` auf Modulebene an eine leere Zeichenkette und in Zeile 143 wird dieser Wert dann ausgegeben. Nirgendwo im Programm wird das `dekodierttext` auf Modulebene an einen anderen Wert gebunden.

Wenn man in einer Funktion etwas an einen Namen bindet, dann ist dieser Name nur lokal innerhalb der Funktion bekannt. Das ist dann ein *anderes* `dekodierttext` was nur innerhalb eines Funktionsaufrufes existiert. Wenn Du Ergebniswerte aus Funktionen haben möchtest, dann musst Du mit Rückgabewerten arbeiten.

Auf keinen Fall solltest Du anfangen mit (modul)globalen Variablen zu arbeiten, so wie Du das hier versuchst. Auf Modulebene sollten nur Konstanten, Funktionen, und Klassen definiert werden. Der Code der das Hauptprogramm ausmacht sollte in einer Funktion stecken. Üblicherweise nennt man die `main()`.

Das was Du mit der äusseren ``while``-Schleife machst ist viel zu umständlich. Man kann direkt über die Elemente von Sequenztypen wie Zeichenketten oder Listen iterieren. Da braucht man nicht selber die Länge ermitteln und einen Index, dann auch noch ”von Hand” aktualisiert, mitschleppen.

Wenn man die Eingabe in Kleinbuchstaben wandelt spart man sich später zwischen Gross- und Kleinschreibung unterscheiden zu müssen.

Die Abbildung von Buchstaben nach Morsesequenzen sollten nicht als Code sondern als Datenstruktur ausgedrückt werden. Dann wird das ganze wesentlich kürzer, übersichtlicher, und weniger fehleranfällig.

Insgesamt würde ich auch noch mal eine Funktion für das de(?)kodieren schreiben die den Text als Argument bekommt und die Morsesequenz als Ergebnis liefert. Das sollte man in einer Liste sammeln und dann am Ende mit der `join()`-Methode auf Zeichenketten zusammenfügen.
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

Jetzt hab ichs so:

Code: Alles auswählen

text = raw_input("Dein-Text: ")
textln = len(text)
akt = 0
dt = ".....- "

def kurz(dt):
    dt = dt + "."

def lang(dt):
    dt = dt + "-"
    
def leer(dt):
    dt = dt + ".....---.."
    

aber am ende kommt nur der erste wert raus?


ich weiß nicht warum....


LG Jannis2711
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

Okay
Benutzeravatar
/me
User
Beiträge: 3555
Registriert: Donnerstag 25. Juni 2009, 14:40
Wohnort: Bonn

Warum gibst du eigentlich über 50 Zeilen mit ein paar Leerzeichen darin aus? Wenn es dir darum geht, den sichtbaren Bildschirm zu löschen, dann reicht auch print ohne Leerzeichen. Und dann schreibt man natürlich nicht den gleichen Code 50mal untereinander sondern man verwendet eine Schleife.

Grundsätzlich sieht der komplette Code gruselig aus, aber zumindest das hätte selbst dir als Anfänger auffallen sollen.

Mal als schnelles Beispiel wie das aussehen könnte.

Code: Alles auswählen

import time
import sys

MORSECODES = {
    ' ': '...----..',
    'a': '.-',
    'b': '-...',
    'c': '-.-.',
    'd': '-..',
    'e': '.,',
    'f': '..',
    'g': '--.',
}


def main():
    text = format(3735928559, 'x')
    print(text)
    for character in text.lower():
        print(MORSECODES[character], end=' ')
        time.sleep(0.3)
        sys.stdout.flush()

if __name__ == '__main__':
    main()
jannis2711
User
Beiträge: 8
Registriert: Freitag 9. Januar 2015, 14:53

Danke nochmal,

das hat mir sehr geholfen.

Das ganze soll nun per GPIO per impuls übertragen werden.. das senden funktioniert 100%ig aber wie empfange ich das.

Ich habe gemacht das es 1 Sekunde für einen (-) langen Ton braucht und eine halbe Sekunde für einen (.) kurzen.

Ich hab 0 Ahnung wie ich das machen sollte

das der empfangsrechner die daten empfängt und wieder in Text zurückübersetzt.
Benutzeravatar
noisefloor
User
Beiträge: 3856
Registriert: Mittwoch 17. Oktober 2007, 21:40
Wohnort: WW
Kontaktdaten:

Hallo,

es gibt doch einen fix- und fertigen Morse-Code Übersetzer, der beide Richtungen kann: https://launchpad.net/pymorsecode

Gruß, noisefloor
Benutzeravatar
noisefloor
User
Beiträge: 3856
Registriert: Mittwoch 17. Oktober 2007, 21:40
Wohnort: WW
Kontaktdaten:

Hallo,

noch was grundsätzliches zum Empfangen: Signal (=Spannung auf einem Pin) zum empfangen reicht _nicht_, du musst die Zeiten zwischen zwei Signalen mit detektieren.

Grund: beim Morsen wird zwischen zwei Zeichen eine einfache Pause gemacht und zwischen zwei Wörten eine dreifache. Besonders die Pause zwischen zwei Zeichen ist extrem wichtig, sonst ist das Dekodieren Trial & Error. Habe ich einmal bei der Quali für die deutsche Geocachingmeisterschaft gemacht, das war die Hölle ;-)

Zur grundsätzlichen Umsetzung: Die GPIO-Bibliothek hat eine Funktion Namens `event_detect`, die eine Callback-Funktion aufrufen kann, wenn ein die Spannung ein einen Pin angelegt wird und auch wieder weg genommen weg. Doku: http://sourceforge.net/p/raspberry-gpio ... ki/Inputs/.

Gruß, noisefloor
Antworten