Почему у меня возникла странная проблема при сравнении экземпляров объектов в IIS 7?

StackOverflow https://stackoverflow.com/questions/611433

Вопрос

У меня действительно странная проблема, которую я не могу решить при сравнении объектов в IIS 7.Мы находимся в процессе развертывания нашего старого приложения на базе IIS 6 ASP.NET на IIS 7, однако у нас возникла проблема со сравнением равенства, которую мы, похоже, не можем решить.

Позвольте мне начать с того, что у меня есть одинаковые сборки и код, запущенные как в IIS 6, так и в IIS 7, однако сравнение объектов отличается с одним и тем же кодом как в IIS 6, так и в IIS 7.Вот пример того, как выглядит мой объект:

class Country : EntityBase {
    public int CountryID { get; set; }
    public string Name { get; set; }

    public override bool Equals(object obj) {
        if (obj == null || !(obj is Country))
            return false;

        Country c = (Country)obj;
        return CountryID == c.CountryID;
    }

    public override int GetHashCode() {
        return CountryID.GetHashCode();
    }
}

У меня есть следующий код на странице ASPX как в IIS 6, так и в IIS 7:

<% foreach(var country in proposalCountries) { %>
<%= country.Country.CountryID %>
<%= country.Country.CountryID.GetHashCode() %>
<%= country.Country.GetHashCode() %>

<%= proposalCountryServices.Count(c => c.Country == country.Country) %>
<%= proposalCountryServices.Count(c => (c.Country != null && country.Country != null) && c.Country.Equals(country.Country)) %>)
<%= proposalCountryServices.Count(c => Object.Equals(c.Country, country.Country)) %>
<% } %>

Вот мои результаты:

IIS 6:

100 <-- CountryID
100 <-- CountryID Hash Code
100 <-- Country Hash Code

1 <-- Something Found
1 <-- Something Found
1 <-- Something Found

IIS 7:

100 <-- CountryID
100 <-- CountryID Hash Code
100 <-- Country Hash Code

0 <-- Nothing Found
1 <-- Something Found
1 <-- Something Found

Есть ли разница между .NET 3.5 SP1 в Windows 2003 и Windows 2008?Я действительно не понимаю, в чем может заключаться проблема.Кто-нибудь сталкивался с подобной проблемой?

Обновление 1:

Чтобы ответить на вопрос Джона.Обе коллекции загружаются с помощью NHibernate .Но я чувствую, что должен повторить, что как IIS 6, так и IIS 7 используют точно такая же сборка приложения, поэтому, если NHibernate или DynamicProxy2 не изменят способ загрузки данных на основе Windows 2003 или Windows 2007, о которых я ничего не смог найти в Google, я не знаю, что с этим делать.

Это также общесистемная проблема всякий раз, когда я сравниваю два своих объекта entity.Таким образом, это может иметь какое-то отношение к оболочке DynamicProxy2, но оба объекта являются объектами Country, и с учетом созданных мной переопределений все должно работать одинаково в IIS 6 и IIS 7.

Обновление 2:

Похоже, это проблема DynamicProxy2 или NHibernate.Потому что я попробовал следующий код:

<%
    var c1 = new ICost.Business.Entities.Country {
        CountryID = 100
    };
    var c2 = new ICost.Business.Entities.Country {
        CountryID = 100
    };
%>
<%= c1.CountryID == c2.CountryID %>
<%= c1.GetHashCode() == c2.GetHashCode() %>
<%= c1.Equals(c2) %>
<%= Object.Equals(c1, c2) %>
<%= c1 == c2 %>

И как для IIS 6, так и для IIS 7 результат был следующим, true, true, true, true, false.Смотрите мой ответ ниже о том, что я сделал, чтобы решить эту проблему.

Обновление 3:

Это тоже могло быть как-то связано с этим:Похоже, вы забыли зарегистрировать http-модуль в Windsor Castle с помощью IIS7

Это было полезно?

Решение 4

Это решение, которое сработало для меня:

public static bool operator ==(BaseEntity a, BaseEntity b)
{
    return Object.Equals(a, b);
}

public static bool operator !=(BaseEntity a, BaseEntity b)
{
    return !Object.Equals(a, b);
}

По-видимому, NHibernate или DynamicProxy творили какую-то магию под Windows 2003, чтобы заставить оператор "==" работать без перегрузки оператора.

Другие советы

Вы не объяснили, что proposalCountries и proposalCountryServices являются.Мне кажется, что ваш метод Equals работает просто отлично, но в IIS7 они содержат разные объекты - у вас есть два объекта с одинаковым идентификатором (поэтому Equals совпадает), но это разные объекты, поэтому == не совпадает.

Пожалуйста, предоставьте подробную информацию о том, как загружаются две коллекции - это, вероятно, и является причиной этого.

разница, которую я вижу, заключается в случае, если вы написали

c.Country == country.Country

и во втором случае это так

c.Country.Equals(country.Country))

так что я бы предположил, что в последнем случае ему это удается, потому что он сравнивает идентификаторы стран обоих объектов, в первом случае, однако, он сравнивает сами объекты.

Почему это работает под IE6, я не знаю...извините

Вы не используете ссылочное равенство (см. Ниже).

Object.Equals вызовет переопределенный метод Equals для вашего типа.

Я подозреваю, что вы извлекли разные экземпляры сущностей из разных DataContexts и добавили их в список, и, следовательно, используя переопределенное Equals, чтобы попытаться заставить его работать.

Обновить:

Извините, не уверен, используете ли вы LINQ2SQL.

Вероятно, вы могли бы устранить проблему, переопределив операторы ==/!=, но есть некоторые соображения, которые следует учитывать и при этом.

Обновление 2:

Чтобы понять, что я имею в виду, найдите оба экземпляра, которые вы считаете равными (именно там, где возникает эта проблема).Установите точку останова.Теперь перейдите &obj1 и введите и &obj2 и введите, вы заметите, что они указывают на разные адреса объектов.Сделайте это как в IIS 6, так и в 7.

Я не уверен, почему он ведет себя по-разному в IIS6 и IIS7, но я подозреваю, что тонкие различия в жизненном цикле страницы могут быть причиной того, что они не равны по ссылкам.

Обновление 3:

Вы работаете в классическом режиме в IIS7?Если нет, попробуйте сделать это.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top