【发布时间】:2011-09-15 15:12:52
【问题描述】:
我有一个问题,这是子集和问题的一个非常明显的例子:
“给定范围 [-65000,65000] 内的整数列表,如果列表的任何子集总和等于 0,则函数返回 true。否则返回 false。”
我想问的是解释而不是解决方案。
这是我在考虑问题的复杂性之前提出的一个特定于实例的解决方案。
- 对数组 A[] 进行排序,并在排序期间将每个元素与计数器“extSum”相加 (O(NLogN))
- 定义指针低 = A[0] 和高 = A[n-1]
- 这里是决定代码:
while(A[low]<0){ sum = extSum; if(extSum>0){ while(sum - A[high] < sum){ tmp = sum - A[high]; if(tmp==0) return true; else if(tmp > 0){ sum = tmp; high--; } else{ high--; } } extSum -= A[low]; low++; high = n - 1; } else{ /* Symmetric code: switch low, high and the operation > and < */ } } return false;
首先,这个解决方案是否正确?我做了一些测试,但我不确定……看起来太容易了……
这段代码的时间复杂度不是O(n^2)吗?
我已经阅读了各种 DP 解决方案,我想了解的是,对于我面临的问题的具体实例,它们比这种幼稚直观的解决方案要好得多。我知道我的方法可以改进很多,但在时间复杂度方面没有什么大不了的......
感谢您的澄清
编辑: 一个明显的优化是,在排序时,如果找到 0,该函数会立即返回 true....但这仅适用于其中有 0 的特定情况数组。
【问题讨论】:
-
如果我正确理解你的代码,你不是假设子集是连续的吗?不一定是这种情况
-
@isbadawi:好吧,我只是假设它会被排序,这是因为我将它作为第一步进行排序。
-
我的意思是例如如果您的输入是 [-4, 1, 4]。一个解决方案是 {-4, 4},但你不会找到它
-
@isbadawi:我认为它确实找到了...如果输入是 [-4,1,4],那么 extSum 将为 1。内部 while 的第一次运行只会递减高(因为 1 - 4
-
我只需要返回 True 或 False,而不是实际的子集......
标签: algorithm computer-science np-complete