Czy możliwe jest konfliktowanie dwóch bibliotek DLL, uniemożliwiając kompilację rozwiązania

9

Chociaż mam konkretny przypadek, ale zastanawiałem się nad ogólną sytuacją.

Czy dwie biblioteki DLL, dodane jako Odniesienie do projektu Visual C #, mogą kolidować ze sobą, aby zapobiec tworzeniu rozwiązania? Jeśli tak jest, jakie są możliwe sposoby złagodzenia tego.

Shamim Hafiz
źródło

Odpowiedzi:

13

To bardzo możliwe.

Jeśli zdefiniowałeś identyczną przestrzeń nazw i wpisz nazwę dla różnych zestawów (lub w swoim projekcie i dodanym zestawie), wystąpi konflikt z dowolnym kodem, który próbuje użyć jednego lub drugiego z tych typów.

Jeśli upewnisz się, że masz unikalne przestrzenie nazw, podobnie jak odniesienia, nie miałbyś tego problemu.

Inna możliwość wiąże się z różnymi wersjami zależności - jeśli twój projekt używa (na przykład) biblioteki rejestrowania w wersji 1.2, ale dodany zestaw ma zależność od tego samego zestawu, ale innej wersji (powiedzmy 1.3) i albo twojego projektu lub dodany zestaw został skonfigurowany / zbudowany do używania określonej wersji, pojawi się konflikt i kompilacja zakończy się niepowodzeniem.

Oba te problemy można rozwiązać za pomocą aliasów zespołu, jak opisano tutaj .

Oded
źródło
Nie jestem do końca pewien, czy to prawda. Jeśli spojrzysz na CIL, CLR odnosi się bezpośrednio do symboli w niektórych zestawach z notacją [zestaw] przed każdym symbolem. Możliwe, że kompilator C # wymusza ten problem, ale nie sądzę, że jest to ograniczenie platformy.
Yam Marcovic
@Yam Marcovic, w jaki sposób osoba sprawdzająca określiłaby przestrzeń nazw, której próbujesz użyć w danej klasie? W pełni kwalifikowane konflikty nazw klas zdecydowanie zapobiegną kompilacji.
Jeremy,
Kompilator C # zapewnia opcję aliasów zestawów, gdy mamy do czynienia ze złożeniami o tej samej nazwie (i ewentualnie mają w nich zdefiniowane te same symbole). Zobacz stackoverflow.com/questions/517058/...
Yam Marcovic,
@Yam - To prawda, ale musisz wiedzieć o tej fladze i używać jej. Samo dodanie zestawu zepsułoby kompilację.
Oded
1
Oczywiście. Dlatego przybywa tu po pomoc, prawda? Chce wiedzieć o tej fladze i używać jej, ponieważ da mu to czystsze rozwiązanie, bez wpływu na jego projekt lub narzędzia innych firm.
Yam Marcovic,
4

Ponieważ nikt o tym nie wspominał, zapytałeś:

jakie są możliwe sposoby złagodzenia tego

Dla tego przypadku istnieje czyste rozwiązanie, bez ograniczeń i bez irytujących obejść. Można zdefiniować aliasy zestawu, aby kompilator wiedział, do których należy się odwoływać we właściwym miejscu.

Zajrzyj na http://blogs.msdn.com/b/ansonh/archive/2006/09/27/774692.aspx

Yam Marcovic
źródło
3

Tak, to bardzo możliwe.
Załóżmy, że dodałeś odwołanie do biblioteki DLL korzystającej ze starej wersji Lucene.Net i chcesz dołączyć najnowszą wersję.
Możesz rozwiązać ten problem, używając zewnętrznych aliasów: http://msdn.microsoft.com/en-us/library/ms173212.aspx

šljaker
źródło
+1 wydaje się, że jest to właściwa odpowiedź, a nie alias „zewnętrzny”.
Jalayn
1

Możesz umieścić dowolną liczbę różnych wersji zestawu w globalnej pamięci podręcznej zestawów pod warunkiem, że mają one silną nazwę. Może to ci pomóc, jeśli chcesz, aby różne aplikacje korzystały z różnych wersji zestawu, jeśli chodzi o maszynę. Jednak używanie różnych wersji zestawu w JEDNEJ aplikacji nadal będzie sprawiało kłopoty.

Jaki jest powód, dla którego potrzebujesz obu wersji jednocześnie?

Jalayn
źródło
1
Cóż, nie dodam wyraźnie różnych wersji. Zasadniczo mam aplikację WPF. Teraz, aby dodać funkcję strony trzeciej, dodałem kilka bibliotek DLL i to te biblioteki DLL mogą być w konflikcie.
Shamim Hafiz,
1
OK, więc może możesz dodać te biblioteki DLL związane z osobami trzecimi do GAC? Dawno nie czytałem o tych rzeczach, ale podejrzewam, że to może rozwiązać twój problem.
Jalayn
Co rozumie się przez GAC tutaj?
Shamim Hafiz
1
Global Assembly Cache, patrz msdn.microsoft.com/en-us/library/yf1d93sz%28v=vs.71%29.aspx
Jalayn
0

Na pewno. Błąd kompilatora „Niejednoznaczne odniesienie” można uzyskać, gdy nie można rozróżnić dwóch obiektów. Zazwyczaj można podać pełną ścieżkę w kodzie i nie spowoduje to problemu, ale jeśli biblioteki dll byłyby w pełni identyczne, nie można w żaden sposób rozróżnić dwóch obiektów. Sya, mamy dwie biblioteki dll:

System.IO, który zawiera klasę File

i

MyProject.IO, który zawiera klasę pliku

Gdybyś miał mieć coś takiego ...

using System.IO;
using MyProject.IO;

...
private void foo()
{
    File f = new File();
}

... miałbyś dwuznaczne odniesienie, ponieważ nie ma sposobu, aby powiedzieć, o którym pliku mówisz. Naprawiłoby to:

using System.IO;
using MyProject.IO;

...
private void foo()
{
    MyProject.IO.File f = new MyProject.IO.File();
}

Jedyny sposób, w jaki trudno byłoby to naprawić, byłby gdyby ścieżka pliku była identyczna w obu zestawach, ale wymagałoby to nieprawdopodobnej sytuacji, w której dwie biblioteki dll miały identyczną strukturę przestrzeni nazw. Na przykład moja powyższa sytuacja nigdy by się nie wydarzyła, ponieważ nikt nie nazwie tam projektu „System” (z wyjątkiem faktycznych programistów frameworku .Net).

Morgan Herlocker
źródło
Właściwie to się często zdarza, jeśli budujesz rozwiązania w oparciu o popularne biblioteki stron trzecich. Na przykład biblioteki Twittera mogą zależeć od starszej wersji biblioteki json lib
Hoàng Long,