проблема с бинарным поиском (вычислить первое, последнее, среднее с новыми значениями)

Приведенный ниже код относится к алгоритму бинарного поиска. Пользователь вводит числа в textbox1 и вводит число, которое он хочет найти с помощью бинарного поиска в textbox2. теперь у меня проблема с этим, я хочу, чтобы при изменении значения mid,first,last он снова запускал функцию. Я имею в виду, например: когда last=mid-1; функция начинается снова и вычисляется с новым значением last (я прокомментировал коды для получения дополнительных пояснений) спасибо

 private void button1_Click(object sender, EventArgs e)
    {
        string strsearchnums = textBox2.Text;
        int result = binarysearch(strsearchnums);
        textBox14.Text = result.ToString();
    }
    public int binarysearch(string strsearchnum)
    {
        string[] source = textBox1.Text.Split(',');
        int[] nums = new int[source.Length];
        for (int i = 0; i < source.Length; i++)
        {
            nums[i] = Convert.ToInt32(source[i]);
        }


        int searchnum = Convert.ToInt32(strsearchnum);
        int first = nums.First();

        int last = nums.Last();

        while (1 <= nums.Length - 1)
        {
            int mid = (int)Math.Floor(nums.Length / 2.0) - 1;

            if (nums[0]> nums[nums.Length-1])
            {
                break;
           }

            if (searchnum < nums[mid])
            {
                last = mid - 1;

         binarysearch(strsearchnum);       ///i thought i should do like this but this isnt correct it becomes stackoverflow    
            }
            if (searchnum > nums[mid])
            {
                first = mid + 1;
      binarysearch(strsearchnum);      ///i thought i should do like this but this isnt correct it becomes stackoverflow    
            }
            if (searchnum == nums[mid])
            {


              return nums[mid];


            }

        }

        return -1; 
    }

person Arash    schedule 25.12.2010    source источник


Ответы (4)


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

   1- Splitt the string with ',' and store in the int[] array.

  string[] strArray = textBox1.Text.split(new string[]{","}, StringSplitOptions.RemoveEmptyEntries);

    List<int> lstInts = new List<int>();      
   foreach(string str in strArray)
   {
      int j;
      int k=0;

      if(int.TryParse(str,out j))
        {
           lstInts.Add(j);
        }
    }
     int[] bsArray = lstInts.ToArray();

   2- Now Sort the Array.
      Array.Sort(bsArray);

   3- Now use Array.Binaryearch() , if you wanna use  framework implementation which is optimized also

      Array.BinarySearch(bsArray, valueToBeSearched)

     if you don't wanna use Framework implementation than follow below algorithm

   public int DoBinarySearchNoNRecursively(int[] array, int value)
    {
        int high = array.Length - 1;

        int low = 0;

        while (low < high)
        {
            int mid = low + (high - low) / 2;

            if (value == array[mid])
                return mid;
            else if (value > array[mid])
                low = mid + 1;
            else if (value < array[mid])
                high = mid;

        }

        return -1;
    }
person TalentTuner    schedule 25.12.2010

Первая проблема заключается в том, что вы никогда не меняете значение strsearchnum, поэтому вы всегда будете получать исключение Stackoverflow, поскольку это бесконечная рекурсия. В общем, для рекурсивного бинарного поиска вы хотите, чтобы ваш метод binarySearch передал искомое число, минимальное и максимальное значение и изменил минимальное и максимальное значение в соответствии с алгоритмом двоичного поиска. Подпись метода должна быть примерно такой

int binarySearch(int min, int max, int num)
{

}

Это должно помочь вам начать работу.

person BrokenGlass    schedule 25.12.2010

я исправил код, как показано ниже, и он исправлен:

 public int binarysearch(int searchnum)
    {
        string[] source = textBox1.Text.Split(',');
        int[] nums = new int[source.Length];
        for (int i = 0; i < source.Length; i++)
        {
            nums[i] = Convert.ToInt32(source[i]);
        }
        int first = 0;
        int last = nums.Length - 1;


        while (1 <= nums.Length)
        {
            int mid = (int)Math.Floor((first + last) / 2.0);
            if (first > last)
            {
                break;
            }
            if (searchnum < nums[mid])
            {
                last = mid - 1;
            }
            if (searchnum > nums[mid])
            {
                first = mid + 1;
            }
            if (searchnum == nums[mid])
            {
                return nums[mid];
            }
        }
        return -1;

    }
person Arash    schedule 25.12.2010

Вот как работает BinarySearch...

Алгоритм бинарного поиска более эффективен, чем алгоритм линейного поиска, но требует сортировки массива.

    // perform a binary search on the data      
     public int binarysearch(string strsearchnum)
{

    string[] source = textBox1.Text.Split(',');
    int[] data = new int[source.Length];
    for (int i = 0; i < source.Length; i++)
    {
        data[i] = Convert.ToInt32(source[i]);
    }


  int low = 0 ; // low end of the search area                
  int high = data.length - 1 ; // high end of the search area
  int middle = ( low + high + 1 ) / 2 ; // middle element    
  int location = -1; // return value; -1 if not found        

  do // loop to search for element
     {


    // if the element is found at the middle               
     if ( searchElement == data[ middle ] )                 
    location = middle; // location is the current middle

    // middle element is too high                      
    else if ( searchElement < data[ middle ] )         
    high = middle - 1 ; // eliminate the higher half
    else // middle element is too low                  
    low = middle + 1 ; // eliminate the lower half  

    middle = ( low + high + 1 ) / 2 ; // recalculate the middle
    } while ( ( low <= high ) && ( location == -1 ) );            

    return location; // return location of search key
   } // end method binarySearch                         
person Ayman Odeh    schedule 29.12.2010