选举投票递归函数 - 斯坦福CS106B问题

时间:2014-05-14 10:49:36

标签: c++ algorithm recursion

我在理解/执行此问题时遇到了一些问题。基本上,这是自我导向的,并且如果有人可以在递归的结构上显示,将会很感激(某种类型的伪代码将被赞赏)。

我坚持的是问题3 - 搜索"每个投票计数。"

http://see.stanford.edu/materials/icspacs106b/H18-Assign3RecPS.pdf

我尝试理解它是您可以生成投票结果的数量,而不会在索引处指定块。如果该块在大多数选票上推动该数字,那么这是至关重要的。但是,我如何将这个想法转化为代码?

澄清 这是他们所指的热身问题,有效,需要改变才能回答上述问题:

bool CanMakeSum(Vector<int> & nums, int targetSum) {

if (targetSum == 0) { 

    counter++;
    cout << listSubset(partial_solution) << endl;

} else {

    for (int i = 0; i < nums.size(); i++) {

        int element = nums[i];

        Vector<int> rest = nums;
        rest.removeAt(i);
        partial_solution.add(element);

        int newTargetSum = targetSum - element;

            if (CanMakeSum(rest, newTargetSum)) {

                return true;

            }

        int remove_place = partial_solution.size() - 1;
        partial_solution.removeAt(remove_place);

    }
}


if (counter > 0) {

    cout << "The number of subsets that exist are: " << counter << endl;
    return true;

}

return false;
}

string listSubset(Vector<int> &partial_solution) {

string solution = "These total up to the sum: ";

for (int i = 0; i < partial_solution.size(); i++) {
    solution += IntegerToString(partial_solution[i]) + " ";
}

return solution;

}

1 个答案:

答案 0 :(得分:1)

你有一些投票块,

std::vector<int> v = { 4, 2, 7, 4 }

共有17票,大多数floor((17 + 1) / 2)或9票可以选举。

让我们假设集合从零开始索引(毕竟它将在一个向量中),并且你想找到第3块(有4票)的关键投票。

首先,构建剩余块的集合:

std::vector<int> r = { 4, 2, 7 }

现在找到该集合的 powerset 。练习引用了你之前可能会使用过的'ListSubsets'功能;这将是相关的。使用std::set和一些递归很容易重新实现。如果您想使用std::vector专门执行此操作,则必须自己进行唯一性测试。

void find_powerset(std::set<std::set<int>> &powerset, std::set<int> initial)
{
  powerset.insert(initial);

  for (auto i = initial.begin(); i != initial.end(); i++)
  {
    std::set<int> new_set(initial);
    new_set.erase(new_set.find(*i));
    find_powerset(powerset, new_set);
  }
}

你可以简单地调用它,

std::set<std::set<int>> powerset;
find_powerset(powerset, std::set<int>(r.begin(), r.end()));

最终会生成这样的内容(当然std::set不会按此顺序保存)。

{ }
{ 4 }
{ 2 }
{ 7 }
{ 4, 2 }
{ 4, 7 }
{ 2, 7 }
{ 4, 2, 7 }

现在简单地将每个子集中的总票数加起来:

0, 4, 2, 7, 6, 11, 9, 13

这些投票结果中有多少未超过多数票数,在与当前票数的投票相结合时,将超过多数票数?您可能会发现练习中的“热身B”任务是相关的。

此步骤可以与前一步骤结合使用,方法是修改上面的powerset函数,只返回其总和落在适当范围内的子集。这留给读者练习。

无论如何,答案是“只有2”,{ 7 }{ 4, 2 }。在所有其他结果中,最终区块的投票不会改变任何内容。简单!