问题描述

给你一个整数数组 Leetcode 一个数组的三等分(C++实现)_数组,只有可以将其划分为三个和相等的非空部分时才返回 true,否则返回 false。
形式上,如果可以找出索引Leetcode 一个数组的三等分(C++实现)_数组_02 且满足 Leetcode 一个数组的三等分(C++实现)_算法_03

示例 1:

输出:Leetcode 一个数组的三等分(C++实现)_数组_04
输出:true
解释:Leetcode 一个数组的三等分(C++实现)_数组_05

示例 2:

输入:Leetcode 一个数组的三等分(C++实现)_数组_06
输出:false

示例 3:

输入:Leetcode 一个数组的三等分(C++实现)_if语句_07
输出:true
解释:Leetcode 一个数组的三等分(C++实现)_数组_08

算法思想

1、可以进行三等分,数组各项元素之和必为3的倍数,否则直接返回false。
2、每一项之和为总数之和的三分之一,通过循环,数组从头至尾只要有连续的三段和相等,且为总数和的三分之一即可。
3、如果出现了三段和相等均为总数和的三分之一但是数组还没有遍历结束也没有关系,因为后面的数字和必为0,不影响题意。

代码实现

class Solution {
public:
bool canThreePartsEqualSum(vector<int>& A) {
int sum = accumulate(A.begin(), A.end(), 0);
if (sum % 3 != 0)
{
return false;
}
int subsum = sum / 3;
int acc_sum = 0;
int count = 0;
for (int i = 0; i < A.size(); i++) // 尽量不要用双重for循环 时间超时
{
acc_sum += A[i];
if (acc_sum == subsum)
{
acc_sum = 0;
count++;
}
if (count == 3) // if语句需要放在for循环里面 如果count等于3但是数组还没有遍历到最后,也说明后序的元素求和为0,不影响题意,此方法完全完全可行。
{
return true;
}
}
return false;
}
};

特别注意

代码中的这个if语句,一定要放到for循环里面,否则count的值大于3的话也可以符合题意 但却返回了false。

if (count == 3) 
{
return true;
}

另一种解法

bool canThreePartsEqualSum(vector<int>& A) {
vector<int>::iterator it1, it2;
for (it1 = A.begin(); it1 != A.end() - 2; it1++)
{
for (it2 = it1 + 1; it2 != A.end() - 1; it2++)
{
int sum1 = accumulate(A.begin(), it1 + 1, 0); // accumulate 特点:左闭右开
int sum2 = accumulate(it1 + 1, it2 + 1, 0);
int sum3 = accumulate(it2 + 1, A.end(), 0);
if ((sum1 == sum2) && (sum2 == sum3))
{
return true;
}
}
}
return false;
}

该方法语义和语法都没有问题,但是调试的时候没有通过,原因就是时间复杂度太高了,超出了预定时间的范围。
注:accumulate的用法:求和的范围为左闭右开的区间。