Announcement

Collapse
No announcement yet.

MySql;Parallelitätsverletzung

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • MySql;Parallelitätsverletzung

    Hi,
    ich frage die Tabelleninhalte einer Reihe von Tabellen mit (ByVal y As Integer) ab, das im 1. Block problemlos funktioniert. Das Ergebnis der Abfrage TrendWert ist auch im 2. Block gültig. Diese Tabelle ist sozusagen die Zusammenfassung aller TrendWerte.
    Im 2. Block wird das Ergebnis richtig eingetragen und bis zur letzten Abfrage auch gespeichert, weil ich mit der Where-Bedingung die Zuordnung verknüpfe. Beim letzten Eintrag bekomme ich die Fehlermeldung:
    Code:
    Parallelitätsverletzung: Der UpdateCommand hat sich auf 0 der erwarteten 1 Datensätze ausgewirkt
    Was ist hier falsch?
    Code:
    	Try
    	  myconn.Open()
    	  Dim com2 As New MySqlCommand("SELECT * FROM trenddaten ORDER BY ZhgZl ASC", myconn)
    	  Dim mySQL As String = "UPDATE trenddaten SET nTrend =?nTrend WHERE ZhgZl ='" & y & "'"
    	  Dim cmd As New MySqlCommand(mySQL, myconn)
    	  cmd.Parameters.Add("?nTrend", MySqlDbType.Double)
    	  cmd.Parameters("?nTrend").Value = TrendWert
    	  'MessageBox.Show(CInt(y) & "  " & TrendWert)	'Kontrolle!
    	  cmd.ExecuteNonQuery()
    	Catch ex As Exception
    	  MessageBox.Show(ex.Message, "Fehler! Datenspeicherung ist fehlgeschlagen!")
    	Finally
    	  Erase lMaxCount
    	  TrendWert = 0
    	  myconn.Close()
    	End Try
    Die nicht konsequente param.Abfrage? Wenn ja, wie erfolgt sie richtig? Da ich weder ein haupt-, noch ein nebenberuflicher Programmierer bin, wäre ich für jede Hilfestellung dankbar.
    Alfred

  • #2
    Hallo Alfred,

    versuche es einmal so:
    [highlight=vbnet]Dim mySQL As String = "UPDATE trenddaten SET nTrend =?nTrend WHERE ZhgZl =?Zl"
    Dim cmd As New MySqlCommand(mySQL, myconn)
    // so geht es etwas kürzer
    cmd.Parameters.Add("?nTrend", MySqlDbType.Double).Value = TrendWert
    cmd.Parameters.Add("?nZl", MySqlDbType.Integer).Value = y
    // so geht es noch besser, aber nur dann,
    // wenn die Datentypen wirklich zusammenpassen
    cmd.Parameters.AddWithValue("?nTrend", TrendWert)
    cmd.Parameters.AddWithValue("?nZl", y)[/highlight]
    Die Namen der Parameter sind ziemlich unwichtig; aber wie bei Deinem "nTrend" ist ein Zusammenhang mit dem dazugehörigen Feld sinnvoll.

    Dein Fehler liegt vermutlich hauptsächlich darin, dass der int-Wert y in Gänsefüßchen gesetzt wird; das ist innerhalb eines Sql-Befehls nur für Strings zulässig und führt zu oft undurchsichtigen Fehlermeldungen. Parameter dagegen werden richtig übergeben.

    Gruß Jürgen

    PS. "eine gediegene Ausbildung"? Schön wärs, dann hätte ich Nachweise über meine Kenntnisse und könnte damit wirklich Geld verdienen. 25 Jahre Eigenstudium und "Learning by doing" mit vielen Kritik in vielen Foren haben mich zu meinem heutigen Kenntnisstand gebracht.

    PS2. Bei Exceptions ist ex.ToString() vorzuziehen, weil es erheblich mehr Informationen liefert.

    Comment


    • #3
      Hallo Jürgen,
      die (liebe) Verwandtschaft hinderte mich, Dir zu antworten.
      Um es vorweg zu nehmen: Beide Varianten erzeugten die Parallelitätsverletzung.
      Code:
      	Try
      	  myconn.Open()
      	  Dim mySQL As String = "UPDATE trenddaten SET nTrend =?nTrend WHERE ZhgZl =?Zl"
      	  Dim cmd As New MySqlCommand(mySQL, myconn)
      	  cmd.Parameters.AddWithValue("?nTrend", TrendWert)
      	  cmd.Parameters.AddWithValue("?Zl", y)
      	  cmd.ExecuteNonQuery()
      	  MessageBox.Show(y & "  " & TrendWert)	'Kontrolle!
      	Catch ex As Exception
      	  MessageBox.Show(ex.ToString())
      	Finally
      	  Erase lMaxCount
      	  TrendWert = 0
      	  myconn.Close()
      	End Try
      Zur Fehlersuche begrenzte ich die ByVal-Loops auf 20 und setzte die MsgBox nach der ExQuerry. Erst nach der 20. Schleife wurde die Exception ausgelöst. Nicht am Anfang, während der Loops, oder bei der letzten Datenübernahme, sondern erst beim Verlassen des Blocks. Für mich als Laien ist diese Sache höchst mysteriös. An den Datentypen kann es auch nicht liegen, weil Spalte: nTrend einen Double-Wert und ZhgZl einen SMALLInt-Wert = 16 Bit) hat. Möglicherweise ist auch ByVal as Integer nicht richtig, denn ich der VB6-Version wurde mit ByVal as String gearbeitet. In der Dokumentation habe ich mit dem Suchparameter Parallelitätsverletzung eine Reihe von Hinweisen gefunden, aber - ich brauche es nicht betonen - in spanischen Dörfern kenne ich mich besser aus
      PS.: Ich will das Thema ja nicht breit treten, aber Deine Lösungskompetenz bei vielen in den Foren gestellten ungelösten komplexen Fragen zwingen jeden Außenstehenden zu meiner Vermutung.
      Grüße Alfred

      Comment


      • #4
        Hallo Alfred,

        wo ist denn die Schleife? Damit könnte es zusammenhängen. Denn dann brauchst Du nur den Wert neu zuzuordnen, aber DbCommand und Parameter nicht neu zu erstellen. Etwa so:
        [highlight=vbnet]myconn.Open()
        Dim mySQL As String = "UPDATE trenddaten SET nTrend =?nTrend WHERE ZhgZl =?Zl"
        Dim cmd As New MySqlCommand(mySQL, myconn)
        cmd.Parameters.Add("?nTrend", MySqlDbType.Double)
        cmd.Parameters.Add("?Zl", MySqlDbType.Integer)
        // mangels VB-Kenntnis hier in Pseudo-Code:
        For (Schleifenvariable var)
        cmd.Parameters("?nTrend").Value = TrendWert // oder woher die Daten kommen
        cmd.Parameters("?Zl").Value = y
        cmd.ExecuteNonQuery()
        Next var[/highlight]
        Int16 und Integer sind (auch unter VB vermutlich) nicht gleich. Aber vom "niedrigen" Typ zum "höheren" ist das Konvertieren sicher kein Problem. Aber wenn es ein Integer ist, sollte er unbedingt als solcher behandelt werden und nicht als String.

        Mir kommt es vor, als bräuchte ich doch ausführlichere Angaben, um noch helfen zu können.

        Gruß Jürgen

        Comment


        • #5
          Hallo Jürgen,
          auch die Schleifenlösung führte zu keinem Erfolg, leider.
          Die Tabelle trenddaten ist die Zusammenfassung der Berechnung von tabellen in denen Einzelberechnungen stattfinden.
          Code:
            Private Sub BlaBlaBla()
          	Dim min As Integer, max As Integer, y As Integer
          	min = 0 : max = n
          	For y = 1 To n
          	  Call BlaBla1(y)
          	  Call BlaBla2(y)
          	  Call BlaBla3(y)
          	  'etc...... 
          	Next
            End Sub
          So ist beispielsweise im Abschnitt
          Code:
          Private Sub BlaBlaBla3(ByVal y As Integer)
          der strittige Block drinnen, der nichts anderes zu tun hätte, als das Rechenergebnis jenem Datensatz zuzuordnen und einzutragen, den y ausweist.
          In VB6 gibt es nicht den geringsten Anstand, allerdings im DAO-Konstrukt und der von mir sehr vermissten, extrem einfachen Datensatzzeigermanipulation. Mit BindingSource ist ja alles besser geworden, angeblich...
          Code:
          Set tdRs = godb.OpenRecordset("SELECT * FROM [TrendDaten] ORDER BY [ZhgZl] ASC", dbOpenDynaset)
          With tdRs
            If .RecordCount > 0 Then .MoveFirst
            JumpTo = y - 1
            .Move JumpTo
              .Edit
              .Fields("nTrend") = lMaxCount(n)
              .Update
          End With
          Es ist 'zum aus der Haut' fahren.
          Grüße Alfred

          Comment


          • #6
            Hallo Alfred,

            ohne dass ich jetzt auf Details (und Deine PN) eingehe: Warum arbeitest Du nicht innerhalb einer jeden DataRow?
            Code:
            foreach(DataRow row in Table1.Rows) {
               // berechne etwas mit dieser row
               // ggf. mit Speicherung in Table2
            }
            Wenn Du mit den Daten per Code etwas machen willst, dann sind DataTable, DataTable.Rows, DataRow die richtigen Klassen. Zugriff auf einen einzelnen Wert z.B. durch row("Feldname") oder row(Index); neue Zeilen werden erstellt durch:
            Code:
            DataRow row = table2.NewRow()
            row.BeginEdit()
            row[0] = ...
            row.EndEdit()
            table2.Rows.Add(row)
            Bis später! Jürgen

            Comment


            • #7
              Hallo Jürgen,
              ja wenn der Wenn nicht wär...
              dann hätte ich schon vor 5 Jahren begonnen mich mit .Net auseinanderzusetzen.
              Mir war schon klar, dass eine 1:1 Umsetzung von VB6 in .Net nicht oder kaum möglich ist.. aber wie so oft 'hapert's meistens am Schluß...
              Der Rest ist nur mehr halb so wild.
              Grüße Alfred

              Comment


              • #8
                Originally posted by Jürgen Thomas View Post
                ohne dass ich jetzt auf Details (und Deine PN) eingehe: Warum arbeitest Du nicht innerhalb einer jeden DataRow?
                Hallo Jürgen,
                ich habe mir Deine Anregungen zu Herzen genommen.
                Mit der Krücke (Anlegen und Speichern in einer Hilfstabelle) und anschließendem Auslesen mit DataReader und dem Eintragen in trenddaten über DataAdapter, CommandBuilder und DataTable sind die Daten genau dort wo sie hingehören. Möglicherweise ist das keine elegante, aber sicher eine zielführende Methode.
                Ich muß mich bei Dir nochmals recht herzlich bedanken. Wenn man die Funktionsweisen versteht (dank Deiner Hilfe war mir das möglich), dann ist .Net halb so wild.
                Grüße Alfred

                Comment

                Working...
                X