日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

java不使用除号实现除法运算_LeetCode29 Medium 不用除号实现快速除法

發布時間:2024/1/23 编程问答 31 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java不使用除号实现除法运算_LeetCode29 Medium 不用除号实现快速除法 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

本文始發于個人公眾號:TechFlow,原創不易,求個關注

鏈接

難度

Medium

描述

給定兩個整數,被除數和除數,要求在不使用除號的情況下計算出兩數的商

Given two integers dividend and divisor, divide two integers without using

multiplication, division and mod operator.

Return the quotient after dividing dividend by divisor.

The integer division should truncate toward zero.

樣例 1:

Input: dividend = 10, divisor = 3

Output: 3

樣例 2:

Input: dividend = 7, divisor = -3

Output: -2

注意:

除數和被除數都在32位int的范圍內

除數不為0

對于超界的情況返回\(2^{31}-1\)

Both dividend and divisor will be 32-bit signed integers.

The divisor will never be 0.

Assume we are dealing with an environment which could only store integers within the 32-bit signed integer range: [?\(2^{31}\), \(2^{31}\) ? 1]. For the purpose of this problem, assume that your function returns \(2^{31}\) ? 1 when the division result overflows.

題解

老規矩,我們依然從最簡單的情況開始入手。我們都知道,在計算機內部,是二進制的,而二進制是只能進行加減的。所以沒錯,所有的乘法和除法的操作其實最終都會轉換為加減法來進行。對于這道題而言也是一樣的,既然禁止我們使用除法,那么我們可以用減法來代替。

暴力

最簡單的策略就是我們可以用一個循環去不停地減,然后用一個累加器計算到底執行了多少次減法,當不夠減的時候則停止。整個流程非常簡單,但是我們還需要考慮一下正負號的問題,按照排列組合來看,被除數和除數一共有4中正負號的情況。但我們并不需要考慮那么多,這四種情況可以簡單地歸并成是否同號兩種,然后進一步分析又會發現是否同號的計算過程并沒有差別,唯一會影響的只有最后結果的正負號。

還有一點比較令人在意的是提示當中說的可能會超界的情況,我們來分析一下,其實會超界的可能性只有一個。那就是\(-2^{31}\)除以-1的情況,會得到\(2^{31}\),而32位int的正數范圍最大是\(2^{31}-1\),所以我們需要在意這個問題。不過好在對于Python而言,int是沒有范圍的,所以可以忽略這個問題,只需要最后特判一下結果,但是對于C++和Java等語言而言,需要特判一下這個case。

我們來總結一下上面的過程,我們可以先將除數和被除數全部轉化為正數,然后用一個標記flag來記錄它們是否同號。再計算完結果之后,需要判斷一下結果的范圍是否越界,如果越界返回\(2^{31}-1\)。

代碼如下:

class Solution:

def divide(self, dividend: int, divisor: int) -> int:

# 判斷是否同號

flag = (dividend > 0 and divisor > 0) or (dividend < 0 and divisor < 0)

ret = 0

# 全部賦值為正

dividend, divisor = abs(dividend), abs(divisor)

start = 0

# 模擬除法

while start + divisor <= dividend:

start += divisor

ret += 1

# 防止越界,注意只有正數才有可能越界

return min(ret, (1 << 31) - 1) if flag else -ret

這個代碼當然是沒有問題的,但是如果你真的這么提交,那么一定會超時。原因也很簡單,當除數非常小,比如是1的時候,那么我們的循環次數就是被除數的大小。當我們給定一個很大的被除數的時候,會超時就是顯然的了。

二進制優化

接下來講的這個算法很重要,是快速冪等許多算法的基礎,由于本題當中不是進行的冪運算,所以不能稱作是快速冪算法,一時間也沒有什么好的名字,由于本質上是通過二進制的運算來優化,所以就稱為二進制優化吧。

在講解算法之前,我們先來分析一下bad case出現的原因。之所以會超時,是因為有可能被除數非常小,比如是1,這個時候我們一位一位地減就非常耗時。那么很自然地可以想到,我們可不可以每次不是減去一個1,而是若干個1,最后把這些減去的數量加起來,是不是會比每次減去一個要更快一些呢?但是還有細節我們不清楚,我們怎么來確定這個每次應該減去的數量呢?如果確定了之后發現不夠減,又應該怎么辦呢?

要回答上面這個問題,需要對二進制有比較深入的理解。我們先把剛才的問題放一放,來看一看二進制對于除法的解釋。舉個簡單的例子,比如15 / 3 = 5。我們知道15等于5個3相乘,那么我們把它們都寫成二進制。15的二進制是1111,3的二進制是0011,5的二進制是0101,我們重點來看這個5的二進制。

5的二進制寫成0101,展開的話會得到是\(2^2 + 2^0 = 4 + 1\),也就是說我們可以把15看成\((2^2+2^0)*3\),這個式子寫成是\((0*2^3+1*2^2+0*2^1+1*2^0)*3=15\)。也就是說我們可以把被除數看成是若干個2的冪乘上除數的和,這就把一個除法問題轉化成了加法問題。同樣我們把求解商轉化成了求解商的二進制表達,二進制表達有了,最后的商無非是再進行一個求和累加即可。

最后,我們來分析一下,為什么能夠優化。因為題目當中已經限定了,除數和被除數都在32位的int范圍。也就是說最多只有32個二進制位,那么我們的循環次數最多也就是32次。通過二進制優化,我們把原本一個\(O(n)\)的問題,降級成了\(O(\log n)\),這兩者之間差了不止一個數量級,當然要快得多。

我們把上面這個思路寫成代碼,就可以得到答案:

class Solution:

def divide(self, dividend: int, divisor: int) -> int:

# 前面處理和之前一樣

flag = (dividend > 0 and divisor > 0) or (dividend < 0 and divisor < 0)

ret = 0

dividend, divisor = abs(dividend), abs(divisor)

# 預處理二進制數組

binary = [0 for _ in range(33)]

# 第0位即2的零次方乘上除數,所以就是除數本身

binary[0] = divisor

for i in range(1, 33):

# 后面每一位是前面一位的兩倍,因為二進制

# << 是位運算左移操作,等價于*2,但是速度更快

binary[i] = binary[i-1] << 1

for i in range(32, -1, -1):

if binary[i] <= dividend:

dividend -= binary[i]

# 答案加上2^i

ret += (1 << i)

return min(ret, (1 << 31) - 1) if flag else -ret

這段代碼不長,也沒有用到什么特別牛哄哄的算法,無非是對二進制的一些運用。但是對于對二進制不夠熟悉的初學者而言,想完全搞明白可能有些費勁,這也是很正常的。希望大家能夠沉下心來好好理解,如果實在看不懂也沒關系,在以后快速冪等算法當中,還會和它見面的。

今天的文章就是這些,如果覺得有所收獲,請順手掃碼點個關注吧,你們的舉手之勞對我來說很重要。

總結

以上是生活随笔為你收集整理的java不使用除号实现除法运算_LeetCode29 Medium 不用除号实现快速除法的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 99小视频| 桃色一区 | 中国女人内精69xxxxxx | 国产精品1024| 日本视频免费在线播放 | 中文不卡av | 久久精品久久精品久久 | 中文字幕亚洲乱码熟女一区二区 | 偷偷操不一样的久久 | 天天爽天天色 | 国产日韩久久 | 秋霞欧美在线观看 | 五月婷婷综合在线 | 91片黄在线观 | 精品国产一区二区三区在线观看 | 四虎成人av | 精品网站 | 亚洲aav| 日本人妻不卡一区二区三区中文字幕 | 国产日韩欧美另类 | 日韩精品2区| 青青草在线视频免费观看 | 九九色在线 | 国产aaaaaa| 久久久精品999 | 日本人六九视频 | 激情www| 国产999在线观看 | 毛片一区二区三区 | 97精品人妻一区二区三区香蕉 | 色妞视频 | 视频在线观看电影完整版高清免费 | 日本一区二区高清免费 | 国产精品一区三区 | 日韩国产精品一区二区 | 被绑在床强摁做开腿呻吟 | 糖心vlog精品一区二区 | 亚洲免费一| 18男女无套免费视频 | 国产精品免费av一区二区 | 农村村妇真实偷人视频 | 久久久久久久国产视频 | 久久sp| 激情小说亚洲色图 | 色欧美日韩 | 蜜臀视频在线播放 | 噜噜av| 深夜福利国产精品 | 2018天天弄| 亚洲第一精品在线 | yy4138理论片动漫理论片 | 日本三级小视频 | 亚洲视频你懂的 | 日韩大尺度视频 | 欧美激情一区二区三区四区 | 性久久久久久久久 | 国产成人综合一区二区三区 | 男人日女人的网站 | 欧美精品在欧美一区二区少妇 | 久操久热 | 久久久噜噜噜 | 久久精品大片 | 欧美xxxxx高潮喷水麻豆 | 嫩草影院菊竹影院 | 泰剧19禁啪啪无遮挡 | 欧美一级黄色网 | 日本一级二级视频 | 色com| 久久资源365 | 国产馆在线观看 | 中文字幕女同女同女同 | 捆绑调教sm束缚网站 | 亚洲视频黄色 | 婷婷在线播放 | 欧美一区二区三区国产 | www国产视频 | 91玉足脚交嫩脚丫在线播放 | 超碰天天| 国产欧美一区二区三区精品酒店 | 九九热国产 | 婷婷成人综合 | 亚洲涩网| 在线观看国产视频 | 91视频看片| 亚洲精华液一区二区 | 国产91传媒 | 久操视频免费观看 | 国产片淫乱18一级毛片动态图 | 久久国产一二三 | 一区二区福利视频 | 精品久久久久久久久久久久久 | 在线亚洲欧美 | 欧美性xxxx在线播放 | 国产成人一区二区三区 | 久草欧美 | 欧美乱轮视频 | 99国产超薄肉色丝袜交足 | 日韩中文av | 激情图片在线观看 |