第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

確定整數(shù)平方根是否為整數(shù)的最快方法

確定整數(shù)平方根是否為整數(shù)的最快方法

紅糖糍粑 2019-06-18 15:38:45
確定整數(shù)平方根是否為整數(shù)的最快方法我在尋找最快的方法來確定long值是一個完全平方(即它的平方根是另一個整數(shù)):我用簡單的方法,使用內(nèi)置的Math.sqrt()函數(shù),但我想知道是否有一種方法可以通過將自己限制在僅為整數(shù)的域來更快地完成它。維護查找表是不切實際的(因為大約有231.5平方小于2的整數(shù)63).下面是我現(xiàn)在所做的非常簡單和直接的方法:public final static boolean isPerfectSquare(long n){   if (n < 0)     return false;   long tst = (long)(Math.sqrt(n) + 0.5);   return tst*tst == n;}注意:我在很多場合都使用這個函數(shù)Euler項目問題。所以沒有其他人需要維護這段代碼。而這種微觀優(yōu)化實際上會產(chǎn)生影響,因為挑戰(zhàn)的一部分是在不到一分鐘的時間內(nèi)完成每一種算法,在某些問題中,這個函數(shù)需要被調(diào)用數(shù)百萬次。我嘗試了解決這個問題的不同方法:經(jīng)過詳盡的測試,我發(fā)現(xiàn)0.5對于Math.sqrt()的結(jié)果是不必要的,至少在我的機器上是不需要的。這個快速逆平方根雖然速度更快,但在n>=410881時卻給出了不正確的結(jié)果。然而,正如博比·沙夫托,我們可以在n<410881的情況下使用FISR黑客。牛頓的方法比Math.sqrt()..這可能是因為Math.sqrt()使用類似于Newton的方法,但在硬件中實現(xiàn),因此它比Java快得多。此外,牛頓的方法仍然需要使用雙倍。一種改進的牛頓方法,它使用了一些技巧,因此只涉及整數(shù)數(shù)學(xué),它需要一些黑客來避免溢出(我希望這個函數(shù)可以處理所有64位的正數(shù)帶符號整數(shù)),它仍然比Math.sqrt().二進制印章甚至更慢。這是有意義的,因為二進制CHOP平均需要16次才能找到64位數(shù)的平方根。根據(jù)約翰的測試or語句在C+中比使用switch,但在Java和C#中,or和switch.我還嘗試創(chuàng)建一個查找表(作為一個由64個布爾值組成的私有靜態(tài)數(shù)組)。然后,而不是要么切換,要么or聲明,我只想說if(lookup[(int)(n&0x3F)]) { test } else return false;..令我驚訝的是,這樣做(只是稍微)慢了一些。這是因為數(shù)組邊界在Java中被檢查.
查看完整描述

3 回答

?
楊魅力

TA貢獻1811條經(jīng)驗 獲得超6個贊

你得做一些基準(zhǔn)測試。最佳算法將取決于輸入的分布。

您的算法可能幾乎是最優(yōu)的,但是您可能需要在調(diào)用平方根例程之前做一次快速檢查,排除一些可能性。例如,看看你的十六進制數(shù)字的最后一個數(shù)字,做一些明智的“和”。完美方格只能以0、1、4或9為底16結(jié)尾,因此對于75%的輸入(假設(shè)它們是均勻分布的),您可以避免對平方根的調(diào)用,以換取一些非??斓奈恍D(zhuǎn)。

Kip對以下實現(xiàn)十六進制技巧的代碼進行了基準(zhǔn)測試。當(dāng)測試數(shù)字1到100,000,000時,此代碼的運行速度是原始代碼的兩倍。

public final static boolean isPerfectSquare(long n){
    if (n < 0)
        return false;

    switch((int)(n & 0xF))
    {
    case 0: case 1: case 4: case 9:
        long tst = (long)Math.sqrt(n);
        return tst*tst == n;

    default:
        return false;
    }}

當(dāng)我在C+中測試類似的代碼時,它的運行速度實際上比原來的要慢。但是,當(dāng)我刪除開關(guān)語句時,十六進制技巧再次使代碼速度提高了一倍。

int isPerfectSquare(int n){
    int h = n & 0xF;  // h is the last hex "digit"
    if (h > 9)
        return 0;
    // Use lazy evaluation to jump out of the if statement as soon as possible
    if (h != 2 && h != 3 && h != 5 && h != 6 && h != 7 && h != 8)
    {
        int t = (int) floor( sqrt((double) n) + 0.5 );
        return t*t == n;
    }
    return 0;}

刪除Switch語句對C#代碼幾乎沒有影響。


查看完整回答
反對 回復(fù) 2019-06-18
  • 3 回答
  • 0 關(guān)注
  • 849 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學(xué)習(xí)伙伴

公眾號

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號