70 votes

Gestion d'ExecuteScalar () lorsqu'aucun résultat n'est renvoyé

J'utilise la requête SQL suivante et la méthode ExecuteScalar () pour extraire des données d'une base de données Oracle:

 sql = "select username from usermst where userid=2"
string getusername = command.ExecuteScalar();
 

Il me montre ce message d'erreur:

System.NullReferenceException: la référence d'objet n'est pas définie sur une instance d'objet

Cette erreur se produit lorsqu'il n'y a pas de ligne dans la table de base de données pour userid=2

Comment dois-je gérer cette situation?

59voto

Branko Dimitrijevic Points 28493

Selon la documentation MSDN pour DbCommand.ExecuteScalar:

"Si la première colonne de la première ligne du jeu de résultats n'est pas trouvé, une référence null (Nothing en Visual Basic) est retourné. Si la valeur dans la base de données est null, la requête renvoie DBNull.De la valeur".

Considérons le fragment de code suivant:

using (var conn = new OracleConnection(...)) {
    conn.Open();
    var command = conn.CreateCommand();
    command.CommandText = "select username from usermst where userid=2";
    string getusername = (string)command.ExecuteScalar();
}

Au moment de l'exécution (testé sous ODP.NET mais il devrait être le même pour tout ADO.NET fournisseur), il se comporte comme cela:

  • Si la ligne n'existe pas, le résultat d' command.ExecuteScalar() est nulle, ce qui est ensuite intégré à une chaîne nulle et affectée à l' getusername.
  • Si la ligne existe, mais a la valeur NULL dans le nom d'utilisateur (est-ce encore possible dans votre base de données?), le résultat de l' command.ExecuteScalar() est DBNull.Value, entraînant un InvalidCastException.

Dans tous les cas, l' NullReferenceException ne devrait pas être possible, alors votre problème est probablement d'ailleurs.

53voto

Rune Grimstad Points 17775

Tout d'abord, vous devez vous assurer que votre objet de commande n'est pas null. Ensuite, vous devez définir la propriété CommandText de la commande sur votre requête SQL. Enfin, vous devriez stocker la valeur de retour dans une variable d'objet et vérifier si elle est nulle avant de l'utiliser:

 command = new OracleCommand(connection)
command.CommandText = sql
object userNameObj = command.ExecuteScalar()
if userNameObj != null then
  string getUserName = userNameObj.ToString()
 ...
 

Je ne suis pas sûr de la syntaxe VB mais vous voyez l'idée.

30voto

Fanda Points 1162

Je viens d'utiliser ceci:

     int? ReadTerminalID()
    {
        int? terminalID = null;

        using (FbConnection conn = connManager.CreateFbConnection())
        {
            conn.Open();
            FbCommand fbCommand = conn.CreateCommand();
            fbCommand.CommandText = "SPSYNCGETIDTERMINAL";
            fbCommand.CommandType = CommandType.StoredProcedure;

            object result = fbCommand.ExecuteScalar(); // ExecuteScalar fails on null
            if (result.GetType() != typeof(DBNull))
            {
                terminalID = (int?)result;
            }
        }

        return terminalID;
    }
 

16voto

Tommy Carlier Points 3954

La ligne suivante:

 string getusername = command.ExecuteScalar();
 

... essayera de convertir implicitement le résultat en chaîne, comme ci-dessous:

 string getusername = (string)command.ExecuteScalar();
 

L'opérateur de casting normal échouera si l'objet est null. Essayez d'utiliser l'opérateur as, comme ceci:

 string getusername = command.ExecuteScalar() as string;
 

9voto

jjj Points 337

cela pourrait aider .. exemple ::

 using System;
using System.Data;
using System.Data.SqlClient;

class ExecuteScalar
{
  public static void Main()
  {
    SqlConnection mySqlConnection =new SqlConnection("server=(local)\\SQLEXPRESS;database=MyDatabase;Integrated Security=SSPI;");
    SqlCommand mySqlCommand = mySqlConnection.CreateCommand();
    mySqlCommand.CommandText ="SELECT COUNT(*) FROM Employee";
    mySqlConnection.Open();

    int returnValue = (int) mySqlCommand.ExecuteScalar();
    Console.WriteLine("mySqlCommand.ExecuteScalar() = " + returnValue);

    mySqlConnection.Close();
  }
}
 

de ce ici

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X