我最近开始学习JavaScript的算法。当我遇到这个问题时,我正在尝试二进制搜索,并且一直在尝试实现它,但是我仍然遇到困难。 该函数接受两个参数(排序后的数组和一个数字),并返回一个object
,其中包含数字的出现和计数。我得到的occurrence
不是数字的正确出现,而count
是常数。
这是我到目前为止所做的:
function binarySearchOccurrence(array, element) {
//declare the start index on the left side to zero
let startIndex = 0;
//declare the end index on the right side to the length of array minus 1
let endIndex = array.length - 1;
//set initial count to zero
let count = 0;
let occurrence = 0;
//declare an empty object to hold the result of search and count
const result = {}
//Applying binary search, iterate while start does not meed end
while(startIndex <= endIndex){
//find the middile index
let middle = Math.floor((startIndex + endIndex)/2);
let guessElement = array[middle];
count++;
//if element is present in the middle, increment occurence
if(guessElement === element){
occurrence++;
while(startIndex <= endIndex){
if(guessElement > element){
endIndex = middle - 1;
occurrence++;
break;
} else {
startIndex = middle + 1;
occurrence++;
break;
}
}
//Else look in the left or right side accordingly
} else if (guessElement > element) {
endIndex = middle - 1;
} else {
startIndex = middle + 1;
}
}
result.occurrence = occurrence;
result.count = count;
return result;
}
当我使用这样的数组进行测试时:binarySearchOccurrence([1, 2, 3, 4, 4, 4, 5, 5, 5, 6, 7, 8, 9], 5)
它返回{ occurrence: 6, count: 4 }
而不是{ occurrence: 3, count: 2 }
;
答案 0 :(得分:0)
您的代码会为每次出现重复计数。
说我们得到了一个数组[5,5,5,5],5。从0,3开始作为开始,结束。 中= 1 因此出现次数将变为1(如果出现则为第一个) 然后在while循环中 否则将计算出else部分,因此出现次数变为2。 现在您以2,3开始,因此mid为2,这又由第一个if语句计算。
替代方法:
我的方法示例。
[1、2、3、4、4、4、4、4、4、5、6、7、8]
binarysearch = bs(arr,val,start,end)=返回val在else -1数组中的位置
pos=bs(arr,val,start,end)
a=pos-1
ppos_a=a
while a!=-1 and a-1>=0:
ppos_a=a
a=bs(arr,val,0,a-1)
b=pos+1
ppos_b=b
while b!=-1 and b+1<=len-1:
ppos_b=b
b=bs(arr,val,b+1,len-1)
result = ppos_b-ppos_a
这应该使您计数。我对复杂性有点怀疑,但似乎是c log n其中c << n
答案 1 :(得分:0)
尝试使用此方法,但是在这种情况下,复杂度将不会是O(n),BST允许右或左子级中的一个等于根节点,将需要额外的计算步骤才能完成对重复节点的搜索被允许。 Are duplicate keys allowed in the definition of binary search trees?
function binarySearchOccurrence(array, element) {
//declare the start index on the left side to zero
let startIndex = 0;
//declare the end index on the right side to the length of array minus 1
let endIndex = array.length - 1;
//set initial count to zero
let count = 0;
let occurrence = 0;
//declare an empty object to hold the result of search and count
const result = {}
//Applying binary search, iterate while start does not meed end
while (startIndex <= endIndex) {
//find the middile index
let middle = Math.floor((startIndex + endIndex) / 2);
let guessElement = array[middle];
count++;
//if element is present in the middle, increment occurence
if (guessElement > element) {
endIndex = middle - 1;
occurrence++;
} else if (guessElement < element) {
startIndex = middle + 1;
occurrence++;
} else if (guessElement === element) {
occurrence++;
count++;
let searchleft = middle; // searchleft == middile index
let searchright = middle;// searchright == middile index
//loop while we donot fine integar < element on left and integar > element on rigth;
while (array[searchright] == guessElement && array[searchleft] == guessElement ) {
if (array[searchright] == element) { //if integar right still equal to element
searchright = searchright - 1;
count++;
occurrence++;
} else if(array[searchleft] == element) { //if integar left still equal to element
searchleft = searchleft + 1;
count++;
occurrence++;
}
}
}
result.occurrence = occurrence;
result.count = count;
return result;
}}
console.log(binarySearchOccurrence([1, 2, 3, 4, 4, 4, 5, 5, 5, 6, 7, 8, 9], 5));
答案 2 :(得分:0)
这个问题是侧边栏的建议,而我在寻找其他问题时,请考虑尝试一下。
我不是一个优秀的JavaScript核心程序员,但是稍微修改了您的代码,我认为下面的代码可以为您提供正确的结果
function binarySearchOccurrence(array, element, flag) {
//declare the start
//index on the left side to zero
let startIndex = 0; //declare the end index on
// the right side to the length of array minus 1
let endIndex = array.length - 1;
//set initial count to zero
let count = 0;
let occurence = -1;
const result = {}
//Applying binary search, iterate while start does not meed end
while (startIndex <= endIndex) { //find the middle index
let middle = Math.floor((startIndex + endIndex) / 2);
count++; //if element is
// present in the middle, increment occurence
if (array[middle] == element) {
occurence = middle;
if (flag == "last") {
startIndex = middle + 1;
} else {
endIndex = middle - 1;
}
} else {
if (arr[middle] > element) {
endIndex = middle - 1;
} else {
startIndex = middle + 1;
}
}
}
result.occurence = occurence;
result.count = count;
return result;
}
function countOccurence(arr, key) {
let count = binarySearchOccurrence(arr, key, "last").count + binarySearchOccurrence(arr, key, "first").count;
let occurence = (binarySearchOccurrence(arr, key, "last").occurence - binarySearchOccurrence(arr, key,
"first").occurence) + 1;
let result = {};
result.occurence = occurence;
result.count = count;
return result;
}
let arr = [0, 1, 2, 3, 4, 4, 4, 4, 5, 6, 7, 8, 9];
console.log(countOccurence(arr, 4));
我的控制台中的输出
{occurence: 4, count: 8}
任何优秀的JS程序员都可以编辑和改进此代码,我将不胜感激。