Ho deciso di non utilizzare un orm e di utilizzare direttamente ADO.NET per il mio progetto. So che ci vorrà più tempo per programmare, ma voglio solo caricare le pagine ad alta velocità anche nei momenti di punta.C# - Quali sono alcune migliori pratiche/suggerimenti ad alte prestazioni per ADO.NET
risposta
Un errore che vedo ripetuto più e più volte:
istanziare e la creazione di tutto (DbConnection, DbCommand, DbParameters) all'interno di un metodo che si chiama più volte in un ciclo stretto.
Nella maggior parte dei casi è possibile eseguire il refactoring delle variabili locali come membri della classe che li istanziano una sola volta e mantengono solo gli aggiornamenti di DbParameters all'interno del metodo.
aggiornato per includere il codice di esempio chiesto nei commenti
responsabilità: Questo è un esempio rapido assemblato per l'unico intento di dimostrare il punto sullo spostamento roba ripetitivo fuori dal giro. Altre buone pratiche non sono necessariamente implementate.
public static void Show() {
List people = new List();
//Everything is done inside the loop
PersonDal personDal = new PersonDal();
foreach (Person person in people) {
personDal.Insert(person);
}
//Things are setup once outside the loop.
using (DbConnection connection = SqlClientFactory.Instance.CreateConnection()) {
// setup the connection
BetterPersonDal betterPersonDal = new BetterPersonDal(connection);
connection.Open();
foreach (Person person in people) {
betterPersonDal.Insert(person);
}
}
}
}
class Person {
public int Id { get; set; }
public string Name { get; set; }
}
In questa prima implementazione, ogni cosa è istituito ogni volta che il metodo viene chiamato:
class PersonDal {
public int Insert(Person person) {
DbProviderFactory factory = SqlClientFactory.Instance;
using (DbConnection connection = factory.CreateConnection()) {
connection.Open();
connection.ConnectionString = "Whatever";
using (DbCommand command = connection.CreateCommand()) {
command.CommandText = "Whatever";
command.CommandType = CommandType.StoredProcedure;
DbParameter id = command.CreateParameter();
id.ParameterName = "@Id";
id.DbType = DbType.Int32;
id.Value = person.Id;
DbParameter name = command.CreateParameter();
name.ParameterName = "@Name";
name.DbType = DbType.String;
name.Size = 50;
name.Value = person.Name;
command.Parameters.AddRange(new DbParameter[] { id, name });
return (int)command.ExecuteScalar();
}
}
}
}
ora passiamo il setup per la costruzione degli oggetti lasciando fuori dal giro:
class BetterPersonDal {
private DbProviderFactory factory;
private DbConnection connection;
private DbCommand command;
private DbParameter id;
private DbParameter name;
public BetterPersonDal(DbConnection connection) {
this.command = connection.CreateCommand();
this.command.CommandText = "Whatever";
this.command.CommandType = CommandType.StoredProcedure;
this.id = command.CreateParameter();
this.id.ParameterName = "@Id";
this.id.DbType = DbType.Int32;
this.name = command.CreateParameter();
this.name.ParameterName = "@Name";
this.name.DbType = DbType.String;
this.name.Size = 50;
this.command.Parameters.AddRange(new DbParameter[] { id, name });
}
public int Insert(Person person) {
this.id.Value = person.Id;
this.name.Value = person.Name;
return (int)command.ExecuteScalar();
}
}
Esempio incluso –
Dai un'occhiata al libro Improving .NET Application Performance and Scalability (disponibile online gratuitamente, in MSDN). C'è un whole chapter sul miglioramento delle prestazioni di ADO.NET.
Link eccellenti. L'unica cosa di cui non sono d'accordo è la loro enfasi sull'utilizzo di stored procedure per le prestazioni. A quanto ho capito, le versioni moderne di SQL Server memorizzano nella cache i piani di esecuzione per le query SQL ad hoc, quindi dopo che una query ad hoc viene eseguita una volta dovrebbe essere veloce come una stored procedure. Tuttavia, l'articolo collegato è in realtà di Microsoft, quindi non ho intenzione di affermare che conosco meglio di loro. In tutti i benchmark che ho fatto ultimamente, tuttavia, le prestazioni delle stored procedure e delle query ad hoc sono praticamente identiche. – MusiGenesis
Un libro davvero ottimo. Ne ho una versione stampata. Sfortunatamente non è stato aggiornato dal 2004 e molte cose sono cambiate. Il backing store di DataRow, ad esempio, è stato completamente riscritto in .Net 2.0, che ha modificato drasticamente il profilo delle prestazioni dell'utilizzo di DataSet tra le versioni 1.xe 2.0. –
essere molto intelligente circa la gestione delle connessioni. L'apertura di una connessione DB può essere molto costosa, quindi tienilo a mente quando scrivi il livello di accesso al database.
Questo non dovrebbe essere un problema finché il pool di connessioni è abilitato. L'istanziazione di un oggetto di connessione e la chiamata al suo metodo 'Open' di solito acquisiscono una connessione disponibile dal pool, piuttosto che stabilire una connessione completamente nuova al database. – LukeH
Concordato con Luca. I collegamenti non valgono la pena di preoccuparsi (molto) per più di 10 anni. – MusiGenesis
Ho ottenuto un codice legacy scritto in VB.Net che ha tutto mescolato come se fosse scritto in VB6: nessun livello, nessuna classe, tutto il codice all'interno del modulo e dei moduli base ... –
Se non si intende utilizzare un ORM, non vengono memorizzati anche i dati? Questo è un grande vantaggio dell'uso di un ORM. Se non è presente una cache di dati, è necessario esaminare i metodi per memorizzare in cache HTML/JavaScript. Questo può essere ottenuto utilizzando la direttiva OutputCache e SqlDependency. O pubblicando file statici HTML e JavaScript. In entrambi i casi, sarai in grado di gestire un carico maggiore se non esegui costantemente il database su ogni richiesta.
Alcuni link:
ASP.NET Web Site Performance Improvement http://www.codeproject.com/KB/aspnet/aspnetPerformance.aspx
10 ASP.NET prestazioni e scalabilità Segreti http://www.codeproject.com/KB/aspnet/10ASPNetPerformance.aspx
blogOmar Al Zabir su ASP.NET Ajax e .NET 3.5 http://msmvps.com/blogs/omar/archive/tags/performance/default.aspx
L'articolo su Martin è eccellente. Vorrei solo aggiungere che si desidera assolutamente utilizzare un DataReader invece di un DataSet (adoro i DataSet, ma non per ragioni di prestazioni).
A meno che non si debba tornare a record precedenti, nel qual caso l'utilizzo di un DataSet può essere una buona idea. –
@Alfred: ha detto che "vuole che le [s] pagine vengano caricate ad alta velocità", quindi presumo che stia parlando di ASP.Net. In questo caso lasciare che un utente torni ai record precedenti in un DataSet significherebbe memorizzare nella cache il DataSet, che probabilmente non sarebbe una buona idea. – MusiGenesis
@MusiGenesis: Non sono in disaccordo con te. Hai detto che ami i DataSet e sto dando un esempio di quando sono adatti. Anche su una pagina web ad alta velocità * super-duper *, qualcuno potrebbe avere una logica che richiede l'accesso ai record precedenti per qualsiasi ragione aziendale. Invece di tornare al database, utilizzare un DataSet. Nessun DataSet sulla cache - niente da fare. Solo un DataSet utilizzato durante la vita della richiesta. –
- 1. Calcolo ad alte prestazioni Python
- 2. Messaggistica JMS ad alte prestazioni
- 3. Matrici multidimensionali C++ ad alte prestazioni
- 4. registrazione multithreading per applicazioni ad alte prestazioni
- 5. Mezzo array ad alte prestazioni
- 6. libreria matematica ad alte prestazioni per .NET/C# e Java
- 7. Espressioni regolari Java semplici ad alte prestazioni
- 8. wpf Grafica ad alte prestazioni 2d
- 9. Timer ad alte prestazioni vs StopWatch
- 10. JRuby/TorqueBox per applicazioni ad alte prestazioni/mission critical
- 11. CSS3 - Quali sono le migliori pratiche sulle prestazioni?
- 12. Quali sono le migliori pratiche sulla formattazione di sql in linea utilizzando ADO.NET in C#
- 13. Buffering ad alte prestazioni per un flusso di randelli
- 14. Griglia pivot ad alte prestazioni per dati pre-aggregati
- 15. Le macchine statiche di Windows Workflow Foundation sono adatte per scenari ad alte prestazioni?
- 16. Visualizzazione dati in tempo reale ad alte prestazioni
- 17. Quali sono i migliori contatori perfmon per un'applicazione ASP.net?
- 18. C/C++ rispetto a Java/C# in applicazioni ad alte prestazioni
- 19. Libri su siti web ad alte prestazioni e scalabilità.
- 20. Serializzazione ad alte prestazioni: Java vs Google Protocol Buffers vs ...?
- 21. Grafica ad alte prestazioni utilizzando il livello WPF Visual
- 22. Analisi RSS/Atom ad alte prestazioni con Ruby on Rails
- 23. Best practice di applicazioni di rete ad alte prestazioni
- 24. Ricerca stringa di massa ad alte prestazioni in Python
- 25. Quali sono le migliori alternative a Lucene?
- 26. Generazione dinamica di funzioni ad alte prestazioni in clojure
- 27. Mappa hash C/C++ ad altissime prestazioni (tabella, dizionario)
- 28. Quali sono i migliori componenti di Boost?
- 29. Cosa sono alcune prestazioni [Dos/Don'ts] in C# -ASP.NET
- 30. Quali sono le migliori risorse per imparare Ant?
Quale database (presumo SQL Server)? – MusiGenesis
Eviterei l'ottimizzazione prematura. – Alex
+1 per l'utilizzo di * plain old * ADO.NET :) –