簡體   English   中英

如何將線性搜索轉換為二進制搜索?

[英]How to convert linear search to binary search?

- 這是我使用Binary Search算法的find()方法:

  • 它的工作與您期望的一樣。 完全沒有問題。

     public int find(long searchKey) { int lowerBound = 0; int upperBound = nElems - 1; int currentIndex; while(true) { currentIndex = (lowerBound + upperBound) / 2; if(a[currentIndex] == searchKey) return currentIndex; // found it! else if(lowerBound > upperBound) return nElems; // can't find it else { // so then divide range if(a[currentIndex] < searchKey) lowerBound = currentIndex + 1; // it's in upper half else upperBound = currentIndex - 1; // it's in lower half } // end else divide range } // end while loop } // end find() method 

這是使用線性搜索的原始insert()方法。 很簡單吧?

public void insert(long value) { // put element into array
    int j;
    for(j=0; j<nElems; j++) // find where it goes
        if(a[j] > value) // (linear search)
            break;
    for(int k=nElems; k>j; k--) // move bigger ones up
        a[k] = a[k-1];
    a[j] = value; // insert it
    nElems++; // increment size
} // end insert()

我需要修改insert()方法以使用find()方法的二進制搜索算法。 到目前為止,這是我想到的。 顯然這是有問題的,但是我似乎找不到問題。 它根本不起作用,即不執行插入操作:

public int insertBS(long value) {
    int lowerBound = 0;
    int upperBound = nElems - 1;
    int curIn;

    while(true) {
        curIn = (lowerBound + upperBound) / 2;
        if(a[curIn] == value)
            return curIn;
        else if(lowerBound > upperBound)
            return nElems;
        else {
            if(a[curIn] < value)
                lowerBound = curIn + 1;
            else
                upperBound = curIn - 1;
        }

        for(int k=nElems; k>curIn; k--) // move bigger one up
            a[k] = a[k-1];
        a[curIn] = value; 
        nElems++; 
    }
}

語言:Java

使用有序數組。

好吧,很明顯為什么不插入該值,這是因為您從未插入該值。 找到插入位置的索引后,您只需從函數中返回即可,無需執行任何操作。

您需要執行二進制搜索以在移動元素之前找到插入索引。 在您的最后一個代碼段中,您試圖在二進制搜索完成之前使用變量curInwhile循環內移動元素。 嘗試將for循環移到while循環之外。

嗯,為什么不只是調用您的查找功能?

public int insertBS(long value) {
    int curIn = find(value); // find where it goes (binary search)
    for(int k=nElems; k>curIn; k--) // move bigger one up
        a[k] = a[k-1];
    a[j] = value; // insert it
    nElems++; // increment size

}

這樣,當您優化/更改查找功能時,插入功能也會更快!

順便提一句,我認為您的find函數不會像編寫的那樣給您預期的行為。 如果您有[0,1,4,5,9]的列表,並且我搜索7,我將得到nElems(5)的索引,由於索引0到4的值都小於n,因此可能會被誤解。 7.似乎有點不耐煩。

int lowerBound = 0;
int upperBound = nElems-1;


int pos = 0;

if(value < a[0])
 pos=0;
else if(nElems>0 && value>a[upperBound])
 pos=nElems;
else
{
 while(nElems>1)
 {
  int j = (lowerBound + upperBound ) / 2;

  if(upperBound - lowerBound ==0)
  {
   pos = lowerBound+1;
   break;              // found it
      }
  else if(upperBound - lowerBound ==1)
  {
   pos=upperBound;  //lo encontre
   break;
  }
  else                          // divide range
          {
           if(a[j] < value)
               lowerBound = j + 1; // it's in upper half
       else
           upperBound = j - 1; // it's in lower half
      }  // end else divide range
 }
}


 for(int k=nElems; k>pos; k--)    // move higher ones up
    a[k] = a[k-1];
 a[pos] = value;                  // insert it
     nElems++;                      // increment size

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM