算法教程:香槟塔问题
香槟塔问题
问题描述
我们将玻璃杯堆成金字塔状,第一排有 1 个玻璃杯,第二排有 2 个玻璃杯,依此类推,直到第 100 排。每个玻璃杯装一杯香槟。
然后,将一些香槟倒入最上面的第一个玻璃杯中。当最上面的玻璃杯装满时,任何多余的液体都会均匀地落到它左右两侧的玻璃杯上。当这些玻璃杯装满时,任何多余的香槟都会均匀地落到这些玻璃杯的左右两侧,依此类推。(最下面一排的玻璃杯中多余的香槟会落到地板上。)
例如,倒完一杯香槟后,最上面的玻璃杯是满的。倒完两杯香槟后,第二排的两个玻璃杯是半满的。倒完三杯香槟后,这两个杯子就满了——现在总共有 3 个满的玻璃杯。倒完四杯香槟后,第三排中间的杯子半满,外面的两个杯子满四分之一,如下图所示。
本质上,这个问题是瀑布级联的建模,是帕斯卡三角形的变体,其中三角形中的每个项目都是其“左父级”和“右父级”的总和。这里,我们需要计算总溢出和,而不是总和。
问题说明
通过阅读问题描述,我们可以了解级联效应,以及塔顶的行如何影响其下方的行。但是,考虑到描述的行/列性质,我们应该开始将“香槟塔”视为数组的数组,其中塔中的每个索引都由一个长度比前一个索引大一的数组组成:
例如:塔 = [ [0], [0,0], [0,0,0], … ]
考虑到这一点,我们不要将塔描绘成如图所示的等边三角形,而是重新设想塔,使每行的索引对齐(直角三角形),并查看它们的值如何相互关联,以了解描述中描述的前 4 次倒酒。
One Pour:
[ 1 ],
[ 0, 0 ],
[ 0, 0, 0 ],
[ 0, 0, 0, 0 ],
Two Pours:
[ 1 ],
[ 0.5, 0.5 ],
[ 0 , 0 , 0 ],
[ 0 , 0 , 0 , 0 ]
Three Pours:
[ 1 ],
[ 1 , 1 ],
[ 0 , 0 , 0 ],
[ 0 ,