3 回答

TA貢獻1877條經驗 獲得超6個贊
偽代碼:
排序清單
循環遍歷排序列表的前半部分,并填充結果列表的所有偶數索引
循環遍歷排序列表的后半部分,并填充結果列表的所有奇數索引
僅p[i]==p[i+1]當輸入的一半以上包含相同元素時,您才可以使用,在這種情況下,除了將相同元素放置在連續的點上之外,別無選擇(根據皮氏孔原理)。
如評論中所指出的那樣,如果其中一個元素至少發生n/2幾次(或n/2+1為奇數n;這種情況一般(n+1)/2)適用于偶數和奇數),則這種方法可能會有太多沖突。最多有兩個這樣的元素,如果有兩個,該算法就可以正常工作。唯一有問題的情況是,至少有一半時間出現一個元素。我們可以通過找到元素并首先對其進行處理來簡單地解決此問題。
我對python不夠了解,無法正確編寫此代碼,因此我自由地從github復制了OP先前版本的實現:
# Sort the list
a = sorted(lst)
# Put the element occurring more than half of the times in front (if needed)
n = len(a)
m = (n + 1) // 2
for i in range(n - m + 1):
if a[i] == a[i + m - 1]:
a = a[i:] + a[:i]
break
result = [None] * n
# Loop over the first half of the sorted list and fill all even indices of the result list
for i, elt in enumerate(a[:m]):
result[2*i] = elt
# Loop over the second half of the sorted list and fill all odd indices of the result list
for i, elt in enumerate(a[m:]):
result[2*i+1] = elt
return result

TA貢獻1799條經驗 獲得超8個贊
已經給出的算法將剩下的不是前一項的最常見項取走是正確的。這是一個簡單的實現,可以最佳地使用堆來跟蹤最常見的堆。
import collections, heapq
def nonadjacent(keys):
heap = [(-count, key) for key, count in collections.Counter(a).items()]
heapq.heapify(heap)
count, key = 0, None
while heap:
count, key = heapq.heapreplace(heap, (count, key)) if count else heapq.heappop(heap)
yield key
count += 1
for index in xrange(-count):
yield key
>>> a = [1,2,3,3,2,2,1]
>>> list(nonadjacent(a))
[2, 1, 2, 3, 1, 2, 3]
添加回答
舉報