2011-06-30 6 views
6

Zasadniczo mam stół z kodami pocztowymi. Pole kodu pocztowego jest zdefiniowane jako "char (5)". Ja najpierw za pomocą kodu, więc mam umieścić te atrybuty na mojej posesji Kod pocztowy:Dlaczego kod first/EF używa "nvarchar (4000)" dla ciągów w surowym poleceniu SQL?

[Key, Column(Order = 0, TypeName = "nchar"), StringLength(5)] 
public string ZipCode { get; set; } 

gdybym zapytania przed tym w EF:

var zc = db.ZipCodes.FirstOrDefault(zip => zip.ZipCode == "12345"); 

Wygenerowany SQL wykorzystuje nvarchar (4000) wstrzykiwać parametry. Huh? Czy to dlatego, że "12345" jest technicznie ciągiem o nieznanej długości? Czy EF nie powinien być na tyle sprytny, aby użyć właściwego "nchar (5)" podczas odpytywania w tabeli?

Pytam, ponieważ zapytanie nvarchar (4000) zajmuje pół sekundy, podczas gdy zapytanie o właściwej odległości jest znacznie szybsze (i mniej czyta).

Każda pomoc/doradztwo byłoby mile widziane.

+0

czy po dodaniu atrybutów do swoich jednostek upuściłeś i ponownie utworzył bazę danych? – BrokenGlass

+0

Jest to wbrew istniejącej bazie danych i nie pozwalam, aby Code First ponownie ją wygenerował. Istniejąca baza danych to zdecydowanie char (5). –

Odpowiedz

2

Służy to wykorzystaniu automatycznej parametryzacji. Poniższy artykuł wyjaśnia ogólną koncepcję, a także dlaczego zastosowano właśnie nvarchar (4000).

http://msdn.microsoft.com/en-us/magazine/ee236412.aspx

+1

Hrm, dziękuję za odpowiedź. Ale myślę, że nadal nie odpowiada, dlaczego EF działa w ten sposób. Czy nie byłoby bardziej wydajne korzystanie z tych samych typów danych podczas generowania zapytań? –

+0

"Kolejnym dobrym zwyczajem, do którego należy się przyzwyczaić w przypadku typów danych opartych na łańcuchach, jest zawsze określenie długości parametru.Ta wartość powinna być długością pola w predykacie SQL, który używa parametru, lub maksymalną długością ciągu (4000 dla NVARCHAR, 8 000 dla VARCHAR), a nie długość samego napisu, autoparametryzacja programu SQL Server zawsze zakłada maksymalną długość ciągu znaków ... "- wydaje mi się, że to informuje, dlaczego podjęli decyzję. Czy nie rozumiem? –

+1

Domyślam się, że to jest dobre dla tego artykułu, ale wydajność zdecydowanie różni się między tymi dwoma pytaniami. To bardzo dziwne, że zespół EF zdecydował się na mniej wydajną trasę. No cóż, przyjmuję twoją odpowiedź. –

1

Czy próbowałeś używać atrybutu MaxLength? This article zawiera godne podsumowanie tego, jak różne atrybuty adnotacji danych są interpretowane przez EF.

+0

Spróbuję użyć MaxLength, dziękuję. Używałem również StringLength i miałem takie samo pytanie, jak twórca tego pytania. Dzięki. – Naomi

+0

MaxLength nie działał dla mnie, może dlatego, że ustawiam atrybuty przy użyciu MetaDataClass? 'code' Klasa publiczna częściowy OperatorMetadata { [kolumnowej (TypeName = "znak")] [StringLength (6)] [MaxLength (6)] publicznego OpCode ciąg {się; zestaw; } – Naomi