2017-09-28 1 views
-2

Ich habe diesen Fehler und ich weiß nicht, was ich falsch mache. Der folgende Code befindet sich im BackRoundWorker.COM-Objekt, das von seinem zugrunde liegenden RCW getrennt wurde, kann nicht verwendet werden. in oledb

kopieren Ausnahme Detail in die Zwischenablage:

System.Runtime.InteropServices.InvalidComObjectException wurde nicht behandelt durch Benutzercode HResult = -2146233049 Message = COM-Objekt, das vom zugrunde liegenden RCW getrennt wurde, kann nicht verwendet werden . Source = mscorlib
Stacktrace: bei System.StubHelpers.StubHelpers.StubRegisterRCW (Object pThis) bei System.Data.Common.UnsafeNativeMethods.IAccessor.ReleaseAccessor (IntPtr hAccessor, Int32 & pcRefCount) bei System.Data.OleDb. (RowBinding.Dispose) bei System.Data.OleDb.OleDbCommand.ResetConnection() bei System.Data.OleDb.OleDbCommand.Dispose (Boolean Entsorgung) bei System.ComponentModel.Component.Dispose() bei AttendanceSystem.Student. frmNewStudent.bgwInsertStudent_DoWork (Objekt Sender, DoWorkEventArgs e) in c: \ Benutzer \ victorbaccaljr \ Desktop \ PROGRAM \ Event Attendace System \ AttendanceSystem \ AttendanceSystem \ Studenten \ frmNewStudent.cs: Linie 138 bei System.ComponentModel.BackgroundWorker.OnDoWork (DoWorkEventArgs e) bei System.ComponentModel.BackgroundWorker.WorkerThreadStart (Object Argument) Innerexception:

Code:

private void bgwInsertStudent_DoWork(object sender, DoWorkEventArgs e) 
    { 
     List<object> arg = (List<object>)e.Argument; 
     bool found = false; 
     using (OleDbConnection cnn = new OleDbConnection(ConfigurationManager.ConnectionStrings["db"].ConnectionString)) 
     { 
      using (OleDbCommand cmd = new OleDbCommand()) 
      { 
       cmd.CommandText = "select top 1 * from [student info] where [email protected]"; 
       cmd.Connection = cnn; 

       cmd.Parameters.Clear(); 
       cmd.Parameters.AddWithValue("@id", arg[0].ToString()); 

       cnn.Open(); 
       using (OleDbDataReader rdr = cmd.ExecuteReader()) 
       { 
        rdr.Read(); 
        if (rdr.HasRows) 
        { 
         found = true; 
        } 
        cnn.Close(); 
       } 
      } 
      using(OleDbCommand cmd=new OleDbCommand()) 
      { 
       if(found) 
       { 
        MessageBox.Show("Student ID already inserted."); 
       } 
       else 
       { 
        cmd.CommandText = "insert into [Student info] values(@id, @firstname, @lastname, @department, @address)"; 
        cmd.Connection = cnn; 

        cmd.Parameters.Clear(); 
        cmd.Parameters.AddWithValue("@id", arg[0].ToString()); 
        cmd.Parameters.AddWithValue("@firstname", arg[1].ToString()); 
        cmd.Parameters.AddWithValue("@lastname", arg[2].ToString()); 
        cmd.Parameters.AddWithValue("@department", arg[3].ToString()); 
        cmd.Parameters.AddWithValue("@address", arg[4].ToString()); 

        cnn.Open(); 
        cmd.ExecuteNonQuery(); 
        cnn.Close(); 

        MessageBox.Show("Record inserted!"); 

        this.DialogResult = DialogResult.OK; 

       } 
      } 
     } 
    } 
+2

Rufen Sie nicht 'cnn.Close()' – ASpirin

+0

Und bitte posten Sie den tatsächlichen Code in Ihrer Frage, verwenden Sie keine Bilder, da es unmöglich ist, sie in den Suchmaschinen zu finden. – HimBromBeere

+3

Mögliches Duplikat von [COM-Objekt, das von seinem zugrunde liegenden RCW getrennt wurde, kann nicht verwendet werden] (https://stackoverflow.com/questions/2260990/com-object-that-has-been-separated-from-its-underingly- rcw-can not-used) –

Antwort

0

Wie erwähnt Aspirin im Kommentar Hier darf man sich Connection.Close auf eigene Faust nennen. Aber das ist keine allgemeine Regel. Sie haben recht, dass die Verbindung geschlossen werden sollte, um nicht verwaltete Ressourcen wie eine Verbindung zur Datenbank oder den Dateihandlern freizugeben. In Ihrem Fall jedoch, da Sie einen umschließenden using -Block haben, der automatisch Dipose aufruft, wenn die Variable den Gültigkeitsbereich verlässt und somit Connection.Close aufruft, wird dieser zweite Aufruf zweimal ausgeführt, was die Ausnahme verursacht, wenn Sie die Verbindung selbst schließen.

Ihre using -Block wäre dies ähnlich:

OleDbConnection con; 
try 
{ 
    con = new OleDbConnection(...); 
    // ... 
    con.Close(); 
} 
finally 
{ 
    if(con != null) con.Close(); 
} 

Close Verursachung zweimal auf einem erfolgreichen Lauf aufgerufen werden.

So können Sie einfach den Anruf an cnn.Close weglassen. weil es schon implizit gemacht wurde.

+0

Ok, ich habe es. Ich vergesse das using() {} wird das Objekt automatisch entsorgen. – Vic

Verwandte Themen