Python Programm mit Testrahmen

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
Christopher H.
User
Beiträge: 2
Registriert: Montag 16. Februar 2009, 08:02

Hallo Python Community

ich habe mir vor diesem Post die Regeln und die Warnung für Studenten durchgelesen... Leider muss ich dieses Thema eröffnen, da ihr unsere einzige Hoffnung seid.
Wir sind Maschinenbauer im 3. Semester und schreiben morgen Einführung in die Informatik. Unser Prof hat uns eine Probeklausur gegeben die wir lösen sollen. ( Ich bitte die Administratoren dieses Thema bitte zu lassen vl kann uns jemand helfen...)

Hier die erste Aufgabe:

In einem vollständigen Python-Programm ist folgende Messreihenauswertung zu programmieren:
- Es ist eine Funktion zu schreiben, an die eine Liste reeller Messwerte zu übergeben ist. In der Funktion ist aus den Messwerten z; i=0, ... , n-1; die in der Mathematischen Statistik wesentliche Kennzahl

hm = sqrt 1/n*(z[0]hoch 2 + z[1]hoch2 + ... + z[n-1]hoch2)

(der ganze Ausdruck ist unter einer Wurzel!)

zu ermitteln. Benutzen Sie für die Quadratwurzel die im Modul math enthaltene Funktion sqrt(x), wobei sowohl das Funktionsresultat als auch das Argument x vom Typ float sind.
Das ermittelte Resultat hm ist an das aufrufende Programm zurückzugeben. In der Funktion ist nicht mit globalen, sondern nur mit lokalen Variablen zu arbeiten.
- In einem Testrahmen (als Hauptprogramm) ist zunächst eine Liste reeller Werte einzulesen. Dabei sei die Anzahl der Messwerte dem Nutzer bekannt und kann zuerst eingelesen werden (Bedingung: 3 <=
Anzahl <= 300). Die Eingabe der Anzahl ist zu wiederholen, solange diese Bedingung verletzt wird (mehrfache Fehleingaben sind nicht auszuschließen). Danach sind die reellen Messwerte mit
Eingabedialog und ohne Eingabefehlerprüfung einzulesen.
Im Testrahmen ist außerdem zu ermitteln, wie viele der eingelesenen Messwerte in das offene Intervall (1, 34.5) fallen, und das Resultat auszugeben.
Schließlich ist die oben erklärte Funktion aufzurufen. Nach der Rückkehr aus dieser Funktion ist das dort ermittelte Resultat hm mit genau 4 Stellen nach dem Dezimalpunkt auszugeben.

Unser Lösung:

Code: Alles auswählen

if__name__==`__main__` 
       n=input("Anzahl der reellen Werte (0<=n<=300):") 
       while n<3 or n> 300: 
               n=input ("Fehler: Noch einmal:") 
      z[] 
      anz=0 
      for i in range (n): 
               print "z[%i]=" %(1+i), 
               z.append(input()) 
               if z[i] > 1 and z[i]< 34.5: 
                           anz=anz+1 
       print "In das Intervall fallen", anz "Werte" 
       res=func(z) 
       print "hm=%.4f" %res 

def func(z): 
       import math 
       hm = 0 
       n=len(z) 
       for i in range (n): 
               hm=hm+z[i]*z[i] 
       hm=math.sqrt(1.0/n*hm) 
       return hm 
Jetzt unser Problem:
- Es ist eine Funktion zu schreiben, an die eine Liste reeller Messwerte zu übergeben ist. In der Funktion ist die Anzahl der positiven Werte (>0) in der übergebenen Liste zu ermitteln. Außerdem ist aus
den Messwerten y[k]; k=0, ... , m-1; der Funktionswert

f= 2/m * Σ (y[k]hoch3 - y[k])

Summe von k=0 bis m-1

zu bestimmen. Nutzen Sie für die Potenz a hoch b die im Modul math enthaltene Funktion pow(a ,b), wobei a, b und die Potenz vom Typ float sind.
Die ermittelte Anzahl und das Resultat f sind an das aufrufende Programm zurückzugeben. In der Funktion ist nicht mit globalen, sondern nur mit lokalen Variablen zu arbeiten.
- In einem Testrahmen (als Hauptprogramm) ist zunächst eine Liste reeller Werte einzulesen. Dabei sei die Anzahl der Messwerte dem Nutzer nicht bekannt. Als Endeerkennungszeichen ist der Wert 5000.0
zu verwenden (es kann vorausgesetzt werden, dass aus physikalischen Gründen alle Listenwerte kleiner als 5000.0 sind). Die Messwerte sind mit Eingabedialog und ohne Eingabefehlerprüfung einzulesen.
Schließlich ist die oben erklärte Funktion aufzurufen. Nach der Rückkehr aus dieser Funktion sind die beiden zurückgegebenen Resultate auszugeben, der Funktionswert f dabei mit genau 2 Stellen nach
dem Dezimalpunkt.

Aber mit dieser Aufgabe kommen wir nicht weiter da wir weder in der Übung noch in der Vorlesung eine Aufgabe mit Enderkennungszeichen hatten!

Es wäre echt super wenn uns jemand eine Python Funktion für diese Aufgabe posten könnte!

MFG
Christopher
Zuletzt geändert von Christopher H. am Montag 16. Februar 2009, 10:39, insgesamt 4-mal geändert.
Pekh
User
Beiträge: 482
Registriert: Donnerstag 22. Mai 2008, 09:09

'Enderkennungszeichen' soll in dem Fall wohl heißen: Wenn ihr beim Durchlaufen der Liste / Datei / wasauchimmer auf den genannten Wert stoßt, soll das Einlesen beendet werden. Wie man eine Schleife beim Eintreten einer Bedingung beendet, habt ihr mit Sicherheit in euren Unterlagen. Solltet ihr das nicht können, habt ihr allerdings noch ganz andere Probleme als Enderkennungszeichen :/

Für eingestellten Code gibt es übrigens das Code-Tag (Button 'Python'). Dann geht die wichtige! Einrückung nicht verloren und ihr bekommt sogar noch farbiges Syntax-Highlighting, was es potentiellen Helfern deutlich angenehmer macht, euren Code zu lesen.
CM
User
Beiträge: 2464
Registriert: Sonntag 29. August 2004, 19:47
Kontaktdaten:

Ui, ui, ui, der Code sieht aber seltsam aus. Aber gut. Ich gebe mal eine Lösung, die etwas (!, *) besser aussieht. Aber dafür beherzigts Du jetzt Pekhs Kritik und Ratschlag mit dem Python-Knopf und versuchst bei Folgepostings schrittweise den Code zu verbessern.

Hier ein Vorschlag:

Code: Alles auswählen

# -*- coding: utf-8 -*-
# imports first!
from math import pow

# nenne die Funktion mal "foo", weil ich ihren wirklichen Namen nicht kenne
def foo(werte):
    laenge = len(werte)
    # hier werden sicher noch 'schönere' Lösungen kommen,
    # aber mir geht es zunächst einmal darum eine 'list comprehension' zu zeigen
    f = 2.0 / laenge * sum([pow(v, k) - v for k, v in enumerate(werte)])
    return f, laenge
    
if __name__ == "__main__":
    # erst eine leere Liste, wo die Werte hereinkommen sollen
    werte = list()
    print "Bitte die Messwerte, Wert für Wert eingeben."
    print "Abbruch der Eingabe erfolgt über den Wert '5000.0'."
    while True:
        # raw_input statt input nutzen!
        # keine Eingabekontrolle ist hier ziemlich wackelig, aber für eine Übungsaufgabe ...
        eingabe = float(raw_input("Bitte den nächsten Messwert eingeben: "))
        if eingabe != 5000.0:
            werte.append(eingabe)
        else:
            break

    wert, laenge = foo(werte)
    print "Wert: %.2f, Länge: %d ." % (wert, laenge)
Hoffe ich habe die Frage richtig verstanden.

HTH
Christian

* PS Der Code läßt sich durchaus noch etwas eleganter schreiben. Aber das ist schon mal ein Anfang.
Panke
User
Beiträge: 185
Registriert: Sonntag 18. März 2007, 19:26

Müsste die LC nicht eher so aussehen:

Code: Alles auswählen

[x**3 - x for x in werte]
CM
User
Beiträge: 2464
Registriert: Sonntag 29. August 2004, 19:47
Kontaktdaten:

Oh ja, natürlich. Ich habe dummerweise y**k gelesen ... :oops:
Christopher H.
User
Beiträge: 2
Registriert: Montag 16. Februar 2009, 08:02

Das ist echt hammer wir flott und nett ihr seid! Vielen Dank :)
Ich habe versucht den ratschlag zu beherzigen!
Ich denke dann werde ich das Programm so übernehmen und morgen anwenden!
Dankeschön
Hab noch ein bisschen anders gemacht!

Code: Alles auswählen

# -*- coding: utf-8 -*- 
# imports first! 
from math import pow 

# nenne die Funktion mal "foo", weil ich ihren wirklichen Namen nicht kenne 
def func(werte): 
    laenge = len(werte) 
    # hier werden sicher noch 'schönere' Lösungen kommen, 
    # aber mir geht es zunächst einmal darum eine 'list comprehension' zu zeigen 
    f = 2.0 / laenge * sum([pow(y, 3) - y for y in werte]) 
    return f, laenge 
    
if __name__ == "__main__": 
    # erst eine leere Liste, wo die Werte hereinkommen sollen 
    werte = list() 
    print "Bitte die Messwerte, Wert für Wert eingeben." 
    print "Abbruch der Eingabe erfolgt über den Wert '5000.0'." 
    while True: 
        # raw_input statt input nutzen! 
        # keine Eingabekontrolle ist hier ziemlich wackelig, aber für eine Übungsaufgabe ... 
        eingabe = float(raw_input("Bitte den nächsten Messwert eingeben: ")) 
        if eingabe != 5000.0: 
            werte.append(eingabe) 
        else: 
            break 

    wert, laenge = func(werte) 
    print "Wert: %.2f, Anzahl der Messwerte: %d ." % (wert, laenge)
Hier noch eine kleine Zusatzaufgabe :)
Wie alt ist der Kapitän?!?!?

Vielleicht kennen Sie die bei Kindern beliebte scherzhafte „Denksportaufgabe“:
Ein Schiff ist 99 Meter lang, hat drei Masten und 157 Quadratmeter Segelfläche; an Bord befinden sich 36 Mann Besatzung, darunter 11 Chinesen und ein Puertoricaner, ferner zwei Hunde, fünf Katzen und ein
Papagei. Wie alt ist der Kapitän?
Der Mathematiker George Pólya (1887-1985) wandelte diesen Kinderscherz in ein echtes Rätsel um:
*************************************************************
Und nun die zu lösende Aufgabe:
Die Länge eines Schiffes in Metern ist eine ganze Zahl, der Kapitän hat Söhne und Töchter – insgesamt nicht mehr 11, und er ist älter als die Anzahl seiner Kinder, aber noch nicht 100 Jahre alt.
Wie alt ist der Kapitän, wie viele Kinder hat er und wie lang ist sein Schiff, wenn das Produkt dieser drei Zahlen 32118 beträgt?
Schreiben Sie ein vollständiges Python-Programm zur Lösung dieser Aufgabe.
*************************************************************
Hinweise zur Lösung:
Die Lösung führt aus mathematischer Sicht auf eine spezielle diophantische Gleichung (siehe
Mathematik):
Gesucht sind ganze Zahlen schiffslaenge, kinderanzahl, kapitaensalter
(mit: 4 <= kinderanzahl <= 11; 4 <kapitaensalter <100), die der diophantischen Gleichung: schiffslaenge * kinderanzahl * kapitaensalter = 32118, genügen.
Solche diophantische Gleichungen können mit dem Computer ohne großes Nachdenken durch „Ausprobieren“ der verschiedenen Kombinationen gelöst werden - immer der Reihe nach:
Im Falle des Kapitän-Rätsels lässt man den Computer einfach von kinderanzahl=4 bis 11 probieren, und zwar jeweils für kapitaensalter von kinderanzahl+1 bis 99. Dabei prüft man, ob die Division von 32118
durch kinderanzahl mal kapitaensalter eine ganze Zahl ergibt (siehe Formel oben).
Wenn ja, berechnet man diese ganzzahlige Schiffslänge:
schiffslaenge = 32118 / (kinderanzahl * kapitaensalter)


Lösung

Code: Alles auswählen

for kinderanzahl in range(4, 12):
  for kapitaensalter in range(kinderanzahl + 1, 100):
    if (32118 % (kinderanzahl * kapitaensalter) == 0):
      schiffslaenge = 32118 / 
                    (kinderanzahl * kapitaensalter)
      print "%i Kinder, der Kapitän ist 
            %i Jahre alt und das Schiff %i Meter lang."
            % (kinderanzahl, kapitaensalter, schiffslaenge)
[/code]
Panke
User
Beiträge: 185
Registriert: Sonntag 18. März 2007, 19:26

Christopher H. hat geschrieben:Das ist echt hammer wir flott und nett ihr seid! Vielen Dank :)
Gerne. Wer richtig fragt, kriegt hier erfahrungsgemäß immer eine gute Antwort. Auch wenn sich in letzter Zeit Beschwerden häufen.
Antworten