簡體   English   中英

在數組中查找大於或等於 N 的數

[英]Find number which is greater than or equal to N in an array

如果我有一個 PHP 陣列:

$array

有價值觀:

45,41,40,39,37,31

我有一個變量:

$number = 38;

如何返回值?:

39

因為那是數組中最接近 38(向上計數)的值?

問候,

泰勒

<?php
function closest($array, $number) {

    sort($array);
    foreach ($array as $a) {
        if ($a >= $number) return $a;
    }
    return end($array); // or return NULL;
}
?>

這是獲得所需結果並適用於任何數組數據的高級過程:

  • 過濾數組,保持大於或等於目標的值,然后 select 最低剩余值。 這是“最佳”值(如果所有值都較小,則可能是“無”)——這是O(n)
  • 或者,先對數據進行排序,然后看下面——這是O(n lg n) (希望如此)

現在,假設數組按 ASCENDING 排序,這種方法可行:

  • 遍歷數組並找到大於或等於目標的第一個元素 - 這是O(n)

如果數組是 DESCENDING (如帖子中所示),請按上述方式執行,但要么:

  • 向后迭代——這是O(n)
  • 首先對它進行排序(參見 fardjad 的回答)——這是O(n lg n) (希望如此)
  • 向前迭代但保留一個后視值(如果精確被跳過,請記住“下一個最高值”)——這是O(n)

快樂編碼。

編輯array_search 上的錯字

喲...似乎很容易。 這是 function

<?php 
$array = array(45,41,40,39,37,31);

   function closest($array, $number){
    #does the array already contain the number?
    if($i = array_search( $number, $array)) return $i;

    #add the number to the array
    $array[] = $number;

    #sort and refind the number
    sort($array);
    $i = array_search($number, $array);

    #check if there is a number above it
    if($i && isset($array[$i+1])) return $array[$i+1];

    //alternatively you could return the number itself here, or below it depending on your requirements
    return null;
}

運行echo closest($array, 38);

這是一個較小的 function 也將返回最接近的值。 如果您不想對數組進行排序(以保留鍵),這很有幫助。

function closest($array, $number) {
    //does an exact match exist?
    if ($i=array_search($number, $array)) return $i;

    //find closest
    foreach ($array as $match) {
        $diff = abs($number-$match); //get absolute value of difference
        if (!isset($closeness) || (isset($closeness) && $closeness>$diff)) {
            $closeness = $diff;
            $closest = $match;
        }
    }
    return $closest;
}

對每個數字進行線性掃描並更新兩個變量,你就完成了。

Python 代碼(性能為 O(N),我認為不可能擊敗 O(N)):

def closestNum(numArray, findNum):
    diff = infinity       # replace with actual infinity value
    closestNum = infinity # can be set to any value
    for num in numArray:
        if((num - findNum) > 0 and (num - findNum) < diff):
            diff = num - findNum
            closestNum = num
    return closestNum

請酌情添加 null 檢查。

如果你真的想要距離上“最接近”的值,即使它的值較小,試試這個,@Jason 得到了大部分的贊譽。

想象一個場景,當您希望在以下情況下最接近 38.9 的數字:

$array = array(37.5, 38.5, 39.5);

當 38.5 更接近時,這里的大多數解決方案都會給你 39.5。 如果您正在查找的內容恰好位於數組中兩個數字之間的中間,則此解決方案只會采用下一個最大值:

function nearest_value($value, $array) {
if (array_search($value, $array)) {
    return $value;
} else {
    $array[] = $value;
    sort($array);
    $key = array_search($value, $array);
    if ($key == 0) { return $array[$key+1]; }
    if ($key == sizeof($array)-1) { return $array[$key-1]; }
    $dist_to_ceil = $array[$key+1]-$value;
    $dist_to_floor = $value-$array[$key-1];
    if ($dist_to_ceil <= $dist_to_floor) {
        return $array[$key+1];
    } else {
        return $array[$key-1];
    }
}
}

它缺乏優雅,它彌補了准確性。 再次感謝@Jason。

試試這個簡單的 PHP function:

<?php
function nearest($number, $numbers) {
    $output = FALSE;
    $number = intval($number);
    if (is_array($numbers) && count($numbers) >= 1) {
        $NDat = array();
        foreach ($numbers as $n)
            $NDat[abs($number - $n)] = $n;
        ksort($NDat);
        $NDat   = array_values($NDat);
        $output = $NDat[0];
    }
    return $output;
}

echo nearest(90, array(0, 50, 89, 150, 200, 250));
?>

為此,我制作了一個較短的 function:

function nearestNumber($num, $array) {
    if(!in_array($num, $array)) $array[] = $num;
    sort($array);
    $idx = array_search($num, $array);
    if(($array[$idx] -$array[$idx-1]) >= ($array[$idx+1] -$array[$idx])) return $array[$idx+1];
    else return $array[$idx-1];
}

在我的情況下效果很好: $array = array(128,160,192,224,256,320); $num = 203 $array = array(128,160,192,224,256,320); $num = 203 :)

它采用最接近的數字,如果兩個數字之間的距離相同(例如我的示例中的 208),則使用下一個最大的數字。

+1 給傑森。

我在下面的實現,但沒有那么快

$array = array(1,2,4,5,7,8,9);

function closest($array, $number) {
    $array = array_flip($array);

    if(array_key_exists($number, $array)) return $number;

    $array[$number] = true;

    sort($array);

    $rendered = array_slice($array, $number, 2, true); 

    $rendered = array_keys($rendered);

    if(array_key_exists(1, $rendered)) return $rendered[1]; 

    return false;
}

print_r(closest($array, 3));

您可以為此使用array_reduce ,這使其更具函數式編程風格:

function closest($needle, $haystack) {
    return array_reduce($haystack, function($a, $b) use ($needle) {
        return abs($needle-$a) < abs($needle-$b) ? $a : $b;
    });
}

對於 rest,這遵循與其他O(n)解決方案相同的原理。

這是我的解決方案。

$array=array(10,56,78,17,30);
$num=65;
$diff=$num;
$min=$num;

foreach($array as $a){
          if( abs($a-$num)< $diff ){
              $diff=abs($a-$num);
              $min=$a;
          }
}

echo $min;

暫無
暫無

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

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