Seite 1 von 1

Immer gleiche Wert in der Liste

Verfasst: Mittwoch 8. Juni 2016, 13:44
von Brando
In folgendem Code wird in der init Methode in eine Liste dreimal das gleiche Objekt eingefügt. Dann werden diesen Objekten, die Vektoren sind (1*3) Zufallszahlen zugefügt. Jetzt ist es so, dass für die drei eingefügten Objekte die Zufallszahlen die gleichen sind. Hängt das damit zusammen, dass bei dem append einer Liste ein call by reference auftritt? Wie könnte man das in ein call by value verwandeln?

Code: Alles auswählen

from sympy.matrices import *
from sympy.printing import *
from IPython.display import display, HTML, Math, Latex, clear_output
from ipywidgets import widgets
from random import randint
from sympy import *
from builtins import str
 
text1 = widgets.Text()
 
button1 = widgets.Button(description="Auswerten")
button2 = widgets.Button(description="Neue Aufgabe")


x=[] 
#x[0] = Matrix()
#x[1] = Matrix()
#x[2] = Matrix()
 
latexWidget = widgets.Latex()
 
taskWidget = widgets.HTML()

 
mhbox1 = widgets.HBox((taskWidget, latexWidget))
mhbox2 = widgets.HBox((button1, button2))
 
def init_vectors(b, matrix_1, anzahl_1, matrix_2):
        global x, text1
        anzahl_matrizen=0;
        for u in range(anzahl_1):
          x.append(matrix_1)
        
        if isinstance(matrix_2,Matrix):
              x.append(matrix_2)
        for u in range(anzahl_1):
           anzahl_matrizen=anzahl_matrizen+1
           for i in range(matrix_1.shape[1]):
              for j in range(matrix_1.shape[0]):
                   x[u][j,i]=randint(-10,10)      
        
        w=widgets.Textarea(
               description='Matrix', 
               value = str(x[0]),
            )
        display(w)
        w=widgets.Textarea(
               description='Matrix', 
               value = str(x[1]),
            )
        display(w)
        if isinstance(matrix_2,Matrix):
             anzahl_matrizen+=1 
             for i in range(matrix_2.shape[1]):
                for j in range(matrix_2.shape[0]):
                    x[anzahl_1][j,i]=randint(-10,10) 
        #w=widgets.Textarea(
               #description='Matrix', 
               #value = str(x[anzahl_1]),
            #)
        #display(w)
        text1.value = ""
        display_task(anzahl_matrizen)
 
def display_task(anzahl_matrizen):
        global x, latexWidget
        a=[]
        clear_output()
        for i in range(anzahl_matrizen):
           b=latex(x[i])
           b=b.replace("left[", "left(")
           b=b.replace("right]", "right)")
           a.append(b)
        
        str1="$\langle" 
        for i in range(anzahl_matrizen):
            str1=str1+a[i]+", "
 
        str1 += "\\rangle$"
        latexWidget.value = str1
 
def evaluate(b):
        global x, y, text1
        z = x.dot(y)
 
        clear_output()
        display_task()
 
        if "{0}".format(z) == text1.value:
                display(HTML("<b><font color='green'>Richtig</font></b>"))
        else:
                display(HTML("<b><font color='red'>Falsch</font></b>"))
 
 
def exec_la_scalar(aufgabentext, matrix1, anzahl1, matrix2):
        taskWidget.value = "<b>{0}</b>".format(aufgabentext)
        init_vectors(button2, matrix1, anzahl1, matrix2)
        button2.on_click(init_vectors)
        button1.on_click(evaluate)
        display(widgets.VBox((mhbox1, text1, mhbox2)))

Re: Immer gleiche Wert in der Liste

Verfasst: Mittwoch 8. Juni 2016, 16:28
von Sirius3
@Brando: Dein Quell-Code hat immer noch die selben Probleme wie der von vor zwei Tagen. Unter anderem solltest Du keine *-Importe machen, keine globalen Variablen verwenden, numpy statt sympy verwenden, weil Du nicht symbolisch sondern mit konkreten Zahlen arbeitest.
Wenn matrix_2 einfach nur ein optionaler Parameter ist, dann gibt es in Python dafür das Singleton None, da braucht man kein isinstance oder sonstige Typprüfung. Es gibt in Python weder call-by-reference noch call-by-value, sondern nur Objekte, die sich nicht auf magische Weise vermehren. Wenn man eine Kopie haben will, dann schreibt man das einfach. Warum übergibst Du init_vectors Matrizen, wenn Du doch sowieso nur die Dimension brauchst um eine Zufallsmatrix zu erzeugen. Das geht übrigens mit einem Einzeiler:

Code: Alles auswählen

random_matrix = numpy.random.randint(-10,10, (anzahl_1,) + shape_1)

Re: Immer gleiche Wert in der Liste

Verfasst: Mittwoch 8. Juni 2016, 16:33
von BlackJack
@Sirius3: Ich habe den Programmablauf nicht komplett verfolgt, aber die `sympy.Matrix`-Objekte werden wohl gebraucht um eine LaTeX-Darstellung für die Anzeige zu bekommen. Wobei der umgekehrte Weg da wahrscheinlich sinnvoller ist, also aus den Daten mit denen man tatsächlich arbeitet (`numpy`-Array) für die Anzeige ein `sympy.Matrix`-Objekt zu erstellen und das dann anzeigen lassen. In diese Richtung bekommt man auch keine Probleme das etwas nicht umgewandelt werden kann.