Array.BinarySearch, где выполняется определенное условие - PullRequest
2 голосов
/ 22 марта 2010

У меня есть массив определенного типа. Теперь я хочу найти запись, в которой выполняется определенное условие.

Каков предпочтительный способ сделать это с тем ограничением, что я не хочу создавать временный объект для поиска, но вместо этого я только хочу дать условие поиска.

MyClass[] myArray;
// fill and sort array..
MyClass item = Array.BinarySearch(myArray, x=>x.Name=="Joe"); // is this possible?

Может быть, можно использовать LINQ для ее решения?

EDIT: Я знаю, что он работает на обычных коллекциях, но мне нужно, чтобы он работал на BinarySearch.

Ответы [ 3 ]

3 голосов
/ 22 марта 2010

Просто используйте FirstOrDefault (или SingleOrDefault, если уникален).

 var myItem =  myArray.FirstOrDefault( x => x.Name == "Joe" );

Или если вы хотите принудительно выполнить BinarySearch и , вы знаете, что массив отсортирован

 var myItem = Array.BinarySearch( myArray,
                                  new MyClass { Name = "Joe" },
                                  new MyClassNameComparer() );

где MyClassNameComparer равен IComparer<MyClass> и сравнивает на основе свойства name.

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

 var myItem = Array.BinarySearch( myArray,
                                  "Joe",
                                  MyClassOrStringComparer() );

Где MyClassOrStringComparer может сравнивать строку с объектом MyClass (и наоборот).

public class MyClassOrStringComparer
{
     public int Compare( object a, object b )
     {
         if (object.Equals(a,b))
         {
             return 0;
         }
         else if (a == null)
         {
             return -1;
         }
         else if (b == null)
         {
             return 1;
         }

         string aName = null;
         string bName = null;

         if (a is string)
         {
             aName = a;
         }
         else
         {
             aName = ((MyClass)a).Name;
         }

         if (b is string)
         {
             bName = b;
         }
         else
         {
             bName = ((MyClass)b).Name;
         }

         return aName.CompareTo( b.Name );
   }
1 голос
/ 22 марта 2010

BinarySearch можно использовать только при сортировке массива и только при поиске определенного значения ключа сортировки.Так что это исключает использование произвольного предиката.

0 голосов
/ 22 марта 2010

Нет, BinarySearch не содержит перегрузки с параметром Comparision <>.Вместо этого вы можете использовать метод LINQ:

MyClass item = myArray.FirstOrDefault(x => x.Name == "Joe");
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...