it4baer
Goto Top

CSharp wpf Datenbankabruf optimieren

Hi,

ich habe einen SELECT welcher im SQL-Developer ~0,03 Sekunden braucht. <- es geht hier nicht um den Select an sich, sondern den Abruf bzw. das wie im Code...

wenn ich diesen mit dieser Methode aufrufe, brauche ich 1,5 Sekunden (was sich relativ lange anfühlt):
        public static DataTable Sql2DataTable(string tns, string query)
        {
            DataTable result = new DataTable();
            try
            {

                using (OracleConnection dbConnection = new OracleConnection(tns))
                {
                    OracleCommand command = dbConnection.CreateCommand();
                    command.CommandText = query;
                    dbConnection.Open();

                    using (OracleDataReader reader = command.ExecuteReader())
                    {
                        bool head = true;
                        while(reader.Read())
                        {
                            string theRow = new string[reader.FieldCount];
                            for (int i = 0; i < reader.FieldCount; i++)
                            {
                                if(head)
                                {
                                    result.Columns.Add(new DataColumn(reader.GetName(i), typeof(string)));
                                }

                                theRow[i] = reader.GetOracleValue(i).ToString();

                            }
                            head = false;
                            
                            result.Rows.Add(theRow);
                        }
                        //result.Load(reader);
                    }
                    //MessageBox.Show("ready"); 

                    dbConnection.Close();
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(query + "\n" + ex.Message);  
            }
            return result;
        }

mit dieser brauche ich sogar 3,5 Sekunden (was untragbar lange ist):
        public static DataTable Sql2DataTable2(string tns, string query)
        {
            DataTable result = new DataTable();
            try
            {
                using (OracleConnection dbConnection = new OracleConnection(tns))
                {
                    OracleCommand command = dbConnection.CreateCommand();
                    command.CommandText = query;
                    dbConnection.Open();

                    using (OracleDataReader reader = command.ExecuteReader())
                    {
                        result.BeginLoadData(); //keine auswirkung
                        result.Load(reader);
                        result.EndLoadData(); //useless
                    }
                    //MessageBox.Show("ready"); 

                    dbConnection.Close();
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(query + "\n" + ex.Message);  
            }
            return result;
        }
    }

=> was mach ich falsch? hat jemand eine Idee für mich?

Vielen Dank

Content-ID: 359926

Url: https://administrator.de/forum/csharp-wpf-datenbankabruf-optimieren-359926.html

Ausgedruckt am: 22.12.2024 um 23:12 Uhr

colinardo
colinardo 04.01.2018 aktualisiert um 19:20:07 Uhr
Goto Top
Nimm einen OracleDataAdapter() und die Fill-Methode damit entfällt das "langwierige" manuelle Füllen einer Datatable mit dem Reader:
https://stackoverflow.com/questions/42360121/fill-datatable-from-oracle- ...
Im DataSet hast du dann dein Ergebnis auch als DataTable.

Grüße Uwe
it4baer
it4baer 05.01.2018 um 09:23:19 Uhr
Goto Top
es ist ein wenig schneller, aber so schnell wie im SQL-Developer ist es nicht annähernd...

=> aber gut, evtl. schafft das C# auch nicht so schnell wie Java

Danke
colinardo
colinardo 05.01.2018 aktualisiert um 09:27:52 Uhr
Goto Top
Zitat von @it4baer:
es ist ein wenig schneller, aber so schnell wie im SQL-Developer ist es nicht annähernd...
Das ist ein "Brot- und Buttervergleich".
it4baer
it4baer 05.01.2018 um 09:33:28 Uhr
Goto Top
Das ist ein "Brot- und Buttervergleich".

Bitte um Erläuterung... was soll das heißen?

Ein SQL-Abruf ist "erstmal" ein SQL-Abruf. Wieso soll ich <Plattform A um an die Daten zu kommen> nicht mit <Plattform B um an die Daten zu kommen> vergleichen können?
colinardo
colinardo 05.01.2018 aktualisiert um 09:52:54 Uhr
Goto Top
Zitat von @it4baer:

Das ist ein "Brot- und Buttervergleich".

Bitte um Erläuterung... was soll das heißen?

Ein SQL-Abruf ist "erstmal" ein SQL-Abruf. Wieso soll ich <Plattform A um an die Daten zu kommen> nicht mit <Plattform B um an die Daten zu kommen> vergleichen können?
Nun du schreibst hier überhaupt nichts über die Umgebung, ob die Connection im Developer Studio(welches das sein soll sagst du ebenfalls nicht, da gibts viele) beständig geöffnet ist (PIPE) , Datenbankzugriffstreiber, Netzwerkumgebung, Firewalls etc. pp.
Visual Studio bietet dir genügend Performance Debugging-Tools mit denen du die Lags schnell identifizierst bzw. die jeweilge verzögernde Routine ausfindig machst. Auch eine Anwendung muss erst mal seine Frameworks in den Speicher laden, Verbindung muss aufgebaut werden, Auth etc.
An bzw. ab "welcher Stelle" du misst ist hier auch nicht klar.
it4baer
it4baer 05.01.2018 um 10:18:55 Uhr
Goto Top
und genau das ist der Punkt...
=> selbstverständlich habe ich das Laden des Programmes und ebenso das öffnen der Datenbank nicht mitgemessen...

ich habe ausschließlich den ABRUF die Query...
=> also von hier:
            DataSet dataSet = new DataSet();
            OracleCommand cmd = new OracleCommand(query);
            cmd.CommandType = CommandType.Text;
            cmd.Connection = connection;

            using (OracleDataAdapter dataAdapter = new OracleDataAdapter())
            {
                dataAdapter.SelectCommand = cmd;
                dataAdapter.Fill(dataSet, "sql");  
            }
bis hier gemessen!

=> die "connection" ist bereits offen!

=> aber natürlich weiß ich nicht wie der SQL-Developer das macht... <- aber darum ging es mir auch nicht, ich wollte die effizienteste Lösung haben, und wenn es diese ist, muss ich damit leben (wir reden hier [bei meinem Abruf] von ~0,2 Sekunden).
colinardo
colinardo 05.01.2018 aktualisiert um 10:27:22 Uhr
Goto Top
Effizienter wirst du das mit .NET nur schwer hinbekommen. Vielleicht mit optimierten clientside Datenbank-Treibern, oder nativ mit C/C++.