在最近的校園Facebook面試中,我要求將一個數組分成3個相等的部分,使得每個數組中的總和大致等於sum/3。
我的方法
1.對數組進行排序
2.填充數組[k](k = 0)uptil(array [k] < = sum/3)3.在此之後,遞增k並重覆上述步驟[k]
有沒有更好的算法,或者是NP硬問題將數組分爲n部分的算法
回答
這是分區問題的一個變種(詳見http://en.wikipedia.org/wiki/Partition_problem)。事實上,解決這個問題可以解決這個問題(取一個數組,填充0,然後解決這個問題),所以這個問題很難。
有一個僞多項式的動態規劃方法。對於從0
開始的每個i
到陣列的大小,您都會跟蹤子陣列的當前大小的所有可能組合以及它們的當前總和。只要陣列的子集數量有限,這個運行速度可以接受得很快。
我會建議的解決方案是爲了「足夠好」的親密度。首先讓我們考慮所有值爲正的簡單問題。然後按值降序排序。三聯陣容。建立三個子集,總是把三元組中最大的一個加到總和最小的那個,最小的到最大的一個,中間到中間。您將最終平均分配陣列,差異將不會超過第三個最小元素的值。
對於一般情況下,你可以分爲積極和消極,每個使用上述方法,然後蠻力所有組合的一組積極,一組否定和中間的少數剩餘值不均勻分配。
如果您有興趣,以下是有關動態編程解決方案的詳細信息。運行時間和內存使用量爲O(n *(sum)^ 2),其中n是數組的大小,sum是數組值的絕對值之和。對於從1到n的每個數組索引j,當您將數組從索引1分割爲3個子集時,存儲所有可能的3個子集總和值。同樣對於每種可能性,存儲一種可能的方式來拆分數組以獲得3個和。然後爲了從1到j的信息將這個信息擴展到1到(j + 1),簡單地把3個和的每個可能的組合分割成1到j,並形成3個和你選擇添加(j + 1)個數組元素分配給3個子集中的任何一個。最後,當你完成並達到j = n時,當你將陣列位置1到n分成3組時,通過3個子集總和的所有組合的集合,並選擇與sum/3的最大偏差爲最小化。起初這可能看起來像O(n *(sum)^ 3)複雜度,但是對於每個j和前兩個子集總和的每個組合,第三子集和是唯一確定的。 (因爲你不允許忽略數組中的任何元素)。因此,複雜性實際上是O(n *(sum)^ 2)。
- 1. 將元組拆分爲n個部分
- 2. 部分排序爲N個未排序組的有效算法
- 3. 將學生劃分爲N組的算法
- 4. 根據項目索引將數組拆分爲N組的算法
- 5. NSFetchedResultsController部分分爲數組
- 6. 將mol2分子的數據庫拆分爲N個較小組
- 7. 將文本分組爲段算法
- 8. 將數組分成較小的部分
- 9. php函數將數組拆分爲3部分,但不包含剩餘部分
- 10. 計算數組部分的平均值
- 11. Java分組算法
- 12. 隨機並將NumPy數組劃分爲不等數部分
- 13. 將數據集劃分爲大小爲n的分箱matlab
- 14. Oracle PL/SQL將csv字符串拆分爲n個部分
- 15. 儘可能均勻地將間隔分爲n部分
- 16. 如何將字符串拆分爲N部分?
- 17. 分組組合算法
- 18. 算法將一組對象分成一定數量的組?
- 19. Tableau - 將數據分爲3個部分
- 20. 將Spark數據幀拆分爲部分
- 21. PHP:如何將數組拆分爲2個部分?
- 22. 根據鍵模式將數組拆分爲多個部分
- 23. 如何計算n的分區數?
- 24. 陣列算法中的分塊數組
- 25. 算法將列表分成組
- 26. 將Ienumerable分爲兩部分
- 27. 在java中使用部分產品的數組乘法運算
- 28. 部分摘要算法(PDP)
- 29. 加入數組的一部分,並將其餘部分保留爲Javascript
- 30. 將N個sql命令拆分爲一個數組?
取決於您是否必須找到最佳解決方案或合理解決方案。獲得最佳解決方案是NP難題。 http://xkcd.com/287/ – Jodrell 2014-11-21 16:08:46
@Jodrell你能解釋一下最好的解決方案是什麼意思 – 2014-11-21 16:11:16
當源數組中沒有項目時,三個組合的距離最近。 – Jodrell 2014-11-21 16:12:43