2008-10-17 13 views
24

Dans ma base de données, dans l'une des tables, j'ai une colonne GUID avec des valeurs nulles. J'ai une méthode avec un guid? paramètre qui insère une nouvelle ligne de données dans la table. Cependant, quand je dis myNewRow.myGuidColumn = myGuid, j'obtiens l'erreur suivante: "Impossible de convertir implicitement le type 'System.Guid?' à 'System.Guid'. "Nullable GUID

Répondre

27

L'API ADO.NET présente certains problèmes lorsqu'il s'agit de gérer des types de valeur NULL (c'est-à-dire qu'elle ne fonctionne tout simplement pas correctement). Nous n'avons eu aucun problème avec ce problème, et nous sommes arrivés à la conclusion qu'il est préférable de définir manuellement la valeur sur null, par ex.

myNewRow.myGuidColumn = myGuid == null ? (object)DBNull.Value : myGuid.Value 

Il est douloureux travail supplémentaire que ADO.NET doit gérer, mais il ne semble pas le faire de manière fiable (même dans 3.5 SP1). Cela fonctionne au moins correctement. Nous avons également vu des problèmes avec le passage des types de valeurs NULL à SqlParameters où le SQL généré inclut le mot clé DEFAULT au lieu de NULL pour la valeur, donc je recommande la même approche lors de la construction des paramètres.

+0

Type d'expression conditionnelle ne peut être déterminée parce qu'il n'y a pas de conversion implicite entre « System.DBNull » et ' System.Guid ' – kjv

+0

Ah, excuses. Fixé. –

+1

Vous pouvez envisager d'utiliser l'opérateur de coalescence null lors de la récupération d'une valeur de remplacement pour un objet nul possible: "(objet) myGuid ?? DBNull.Value" –

9

OK; Comment myGuidColumn est-il défini et comment myGuid est-il défini?

Si myGuid est Guid? et myGuidColumn est Guid, l'erreur est correcte: vous devez utiliser myGuid.Value ou (Guid)myGuid pour obtenir la valeur (qui jetteront si elle est nulle), ou peut-être myGuid.GetValueOrDefault() pour retourner le zéro guid si null. Si myGuid est Guid et myGuidColumn est Guid?, alors cela devrait fonctionner.

Si myGuidColumn est object, vous avez probablement besoin de DBNull.Value au lieu de la valeur null régulière.

Bien sûr, si la colonne est vraiment annulable, vous pourriez tout simplement envie de vous assurer qu'il est Guid? dans le code C# de

1

Vous pouvez utiliser une méthode d'assistance:

public static class Ado { 
    public static void SetParameterValue<T>(IDataParameter parameter, T? value) where T : struct { 
     if (null == value) { parameter.Value = DBNull.Value; } 
     else { parameter.Value = value.Value; } 
    } 
    public static void SetParameterValue(IDataParameter parameter, string value) { 
     if (null == value) { parameter.Value = DBNull.Value; } 
     else { parameter.Value = value; } 
    } 
} 
2

ou :

internal static T CastTo<T>(object value) 
    { 
     return value != DBNull.Value ? (T)value : default(T); 
    } 
3

Si vous voulez éviter de travailler avec GUIDs nullables dans votre code C# (personnellement, je trouve souvent lourd à travailler avec des types nullable) vous pourriez quelque part tôt le cul ign Guid.Empty aux données .NET qui est nulle dans la base de données. De cette façon, vous n'avez pas à vous soucier de toutes les choses .HasValue et vérifiez simplement si myGuid != Guid.Empty à la place.

+0

J'utilise déjà un GUID vide avec un "sens" différent. – kjv

5

même que la réponse Greg Beech

myNewRow.myGuidColumn = (object)myGuid ?? DBNull.Value 
4

Essayez de System.Guid.Empty où vous voulez qu'il soit null

1

Si vous êtes dans les méthodes d'extension ...

/// <summary> 
/// Returns nullable Guid (Guid?) value if not null or Guid.Empty, otherwise returns DBNull.Value 
/// </summary> 
public static object GetValueOrDBNull(this Guid? aGuid) 
{ 
    return (!aGuid.IsNullOrEmpty()) ? (object)aGuid : DBNull.Value; 
} 

/// <summary> 
/// Determines if a nullable Guid (Guid?) is null or Guid.Empty 
/// </summary> 
public static bool IsNullOrEmpty(this Guid? aGuid) 
{ 
    return (!aGuid.HasValue || aGuid.Value == Guid.Empty); 
} 

Ensuite, vous pourriez dire: myNewRow.myGuidColumn = myGuid.GetValueOrDBNull();

NOTE: Cette volonté insérez null quand myGuid == Guid.Empty, vous pouvez facilement ajuster la méthode si vous voulez autoriser des Guids vides dans votre colonne.

5

Vous avez jeter null à un nullable Guid, ce comment cela a fonctionné pour moi:

myRecord.myGuidCol = (myGuid == null) ? (Guid?)null : myGuid.Value 
0
Guid? _field = null; 
if (myValue!="")//test if myValue has value 
{ 
_field = Guid.Parse(myValue) 
}