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

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

1000个瓶子里面999瓶是水,多少次试验确定哪瓶是毒药

發(fā)布時(shí)間:2023/12/9 编程问答 52 豆豆
生活随笔 收集整理的這篇文章主要介紹了 1000个瓶子里面999瓶是水,多少次试验确定哪瓶是毒药 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

題圖 | @望川鳥


本文來自寒食君的投稿,公眾號(hào):字節(jié)流

在文章之前我先拋出一個(gè)有趣的問題,相信有的同學(xué)是看過的,沒有看過的也不打緊兒,文章下面會(huì)進(jìn)行解答。問題如下:

現(xiàn)在有1000個(gè)瓶子,里面999瓶是水,1瓶是毒藥。最少通過多少次的試驗(yàn),能確定哪瓶是毒藥。

這個(gè)問題你可以思考一下,我先來說一說最近在生活中遇到的另一間相關(guān)的事。

前段時(shí)間在設(shè)計(jì)一張數(shù)據(jù)表的時(shí)候遇到了一個(gè)小問題。情況是這樣的,一條數(shù)據(jù)有著三種狀態(tài),這三種狀態(tài)是可能疊加并且重復(fù)的。什么意思呢?我舉一個(gè)通俗的例子來類比一下。

孔子曰:吾日三省吾身。高乎?帥乎?富乎?高、富、帥可以說是一個(gè)人的三種狀態(tài)。比如通過「骨骼生長(zhǎng)」這個(gè)函數(shù)的處理,人可以擁有「高」這個(gè)狀態(tài);通過「自我打理、運(yùn)動(dòng)健身」這個(gè)函數(shù)的處理,人可以擁有「帥」這個(gè)狀態(tài);通過「發(fā)奮圖強(qiáng)」這個(gè)函數(shù)的處理,人可以擁有「富」這個(gè)狀態(tài)。什么是疊加?就是一個(gè)人可以擁有其中的多種狀態(tài);什么是重復(fù)?比如一個(gè)人多次「奮發(fā)圖強(qiáng)」,依然會(huì)擁有「富」的狀態(tài)。

解釋完這些,再回到問題本身。我當(dāng)時(shí)想的是,給每個(gè)狀態(tài)一個(gè)單獨(dú)的布爾類型(可以判斷真或假)的字段,然后在進(jìn)行處理時(shí)對(duì)相應(yīng)狀態(tài)進(jìn)行分別判斷。這樣雖然也能完成任務(wù),但是顯得笨重且不優(yōu)雅。舉兩個(gè)顯而易見的例子:

  • 假如這條數(shù)據(jù)將來不止三種狀態(tài),難道需要重新對(duì)數(shù)據(jù)庫進(jìn)行改造嗎?而且程序也要相應(yīng)地修改。數(shù)據(jù)庫作為基礎(chǔ)設(shè)施,一旦確定,修改地成本是很高的。

  • 因?yàn)橐粭l數(shù)據(jù)可能會(huì)經(jīng)過多次相同類型地處理,假如這樣設(shè)計(jì),每次處理前程序都需要知道當(dāng)前狀態(tài)是真是假,處理完再?zèng)Q定是否修改狀態(tài)碼。這會(huì)導(dǎo)致程序的冗余、不簡(jiǎn)潔。

  • ...

  • 針對(duì)這些問題,X叔(組里一位我很敬重的老哥)建議我可以用一個(gè)籠統(tǒng)的字段 status,然后每種狀態(tài)的值可以設(shè)置為1、2、4...這樣。我心想,妙啊。

    多重狀態(tài)疊加產(chǎn)生的值是不會(huì)產(chǎn)生重復(fù)的,比如「高富」=3,「高帥」=5,「富帥」=6等等。而且以后有新的狀態(tài),假設(shè)新增「健康」這些,到時(shí)候,直接約定為相應(yīng)值8、16等等。

    那這和位運(yùn)算有什么關(guān)系呢?我們來看下面這張圖。

    而在重復(fù)處理方面,位與運(yùn)算帶來了更加簡(jiǎn)潔的操作。舉個(gè)例子,假如當(dāng)前狀態(tài)時(shí)是「高帥」,需要再次進(jìn)行「帥」處理,如果按照傳統(tǒng)的加減方式,需要判斷當(dāng)前有沒有「帥」這個(gè)狀態(tài)4,有的話不加,沒有的話加上4。這無疑是非常繁瑣的。

    使用位與運(yùn)算,會(huì)簡(jiǎn)潔很多,比如:

    很方便。在進(jìn)行位或的時(shí)候也是如此,可以結(jié)合具體情況試一試。

    除此之外,在一些編程語言的源碼里,經(jīng)常會(huì)用到位運(yùn)算,因?yàn)樗粌H高效,而且有時(shí)候更靈活。比如JDK8里在優(yōu)化HashMap的擴(kuò)容時(shí),將取模運(yùn)算換成了位運(yùn)算。可以參考上篇滴滴好用,但是不安全。HashMap:我也是。


    解決了這個(gè)問題。回頭看看文章開頭的智力題。

    可以先公布一下答案:10。

    假設(shè)現(xiàn)在有十只小白鼠,如何10只小白鼠的生死來找出那一瓶毒藥呢?我們先將1000個(gè)瓶子用二進(jìn)制編號(hào),就像下圖:

    從000000001-1111111111,代表1號(hào)到1024號(hào)(1001-1024個(gè)瓶子可以忽視,因?yàn)橹恍枰?000個(gè)),可以看到,每個(gè)數(shù)都有十位,那么我們讓每只小白鼠負(fù)責(zé)一列,將這一列的編號(hào)出現(xiàn)1的瓶子中的液體混合著喝下去。如果某只小白鼠死了那么可以判定這列為1的所有瓶子中,有一瓶是毒藥。通過十只小白鼠的生死情況組合來看,不難發(fā)現(xiàn)那瓶是毒藥的瓶子編號(hào)。

    如果你覺得數(shù)量太大,有些納悶,可以減少數(shù)量,假設(shè)總共共有八個(gè)瓶子,其中一瓶是毒藥。仔通過這種方式來計(jì)算一下。

    總結(jié)

    以上是生活随笔為你收集整理的1000个瓶子里面999瓶是水,多少次试验确定哪瓶是毒药的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。