[英]Longest Even Length Substring in an array
我使用一维数组解决了一个问题( 最长偶数长度 Substring )。 但我不知道我的代码有什么问题。 它失败了。 您能否分析我的代码并通过适当的示例解释我的方法失败的原因。
#include<iostream>
using namespace std;
int main()
{
int t;
string number;
cin>>t;
while(t--) {
cin>>number;
int current=0,prev=0;
int length = number.length();
int sum[length],n1,n2;
sum[0] = number[0]-'0';
for(int i=1; i<length; i++) {
sum[i] = sum[i-1] + (number[i]-'0');
}
for(int i=0; i<length; i++) {
for(int j=i+1;j<length;j=j+2) {
int value;
if(i==0) value = sum[j]; else value = sum[j]-sum[i-1];
if(value%2 == 0) {
int index = (i+j)/2;
if(index == 0) {
n1 = sum[0];
n2 = sum[j];
}
else {
int data;
if(i==0) data = 0; else data = sum[i-1];
n1 = sum[index]-data;
n2 = sum[j]-sum[index];
}
if(n1==n2 ){
if( (j-1+1) > prev) {
prev=current=j-i+1;
}
}
}
}
}
cout<<current<<"\n";
}
return 0;
}
给你:
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <iterator>
int main() {
int t;
std::cin >> t;
int i;
std::string str;
std::vector<std::vector<int>> px(t);
for (i = 0; i != t; ++i) {
std::cin >> str;
px[i].reserve(str.size() + 1);
px[i].emplace_back(0);
for (auto const& ch : str) {
px[i].emplace_back(px[i].back() + ch - '0');
}
}
std::vector<int> ans;
ans.reserve(t);
int k, k_max, pp, pp_lim, lhs, rhs, tmp, max;
for (auto const& v : px) {
max = 0;
for (k = 1, k_max = (v.size() - 1) >> 1; k <= k_max; ++k) {
for (pp = k, pp_lim = v.size() - k; pp != pp_lim; ++pp) {
lhs = v[pp] - v[pp - k];
rhs = v[pp + k] - v[pp];
if (lhs == rhs) {
tmp = k << 1;
if (tmp > max) {
max = tmp;
}
}
}
}
ans.emplace_back(max);
}
std::copy(ans.cbegin(), ans.cend(), std::ostream_iterator<int>(std::cout, "\n"));
return 0;
}
您正在尝试实现前缀和算法,但不幸的是您做错了。 让我们看一下第二个str,即“1234123”。 它的前缀总和看起来像这样:
0 1 3 6 10 11 13 16
k 在这种情况下属于范围 [1; (8 - 1)/2 或 (8 - 1) >> 1],其中 (8 - 1) 是 "1234123" 的 the.size() 而 8 是 v 的 the.size() 是保持“1234123”的前缀总和。 让我们看一下我们可以得到的总和:
k = 1
1 = 2 -> v[1] - v[1 - k] = v[1 + k] - v[1]
2 = 3 -> v[2] - v[2 - k] = v[2 + k] - v[2]
3 = 4 -> v[3] - v[3 - k] = v[3 + k] - v[3]
4 = 1 -> v[4] - v[4 - k] = v[4 + k] - v[4]
1 = 2 -> v[5] - v[5 - k] = v[5 + k] - v[5]
2 = 3 -> v[6] - v[6 - k] = v[6 + k] - v[6]
k = 2
1 + 2 = 3 + 4 -> v[2] - v[2 - k] = v[2 + k] - v[2]
2 + 3 = 4 + 1 -> v[3] - v[3 - k] = v[3 + k] - v[3]
3 + 4 = 1 + 2 -> v[4] - v[4 - k] = v[4 + k] - v[4]
4 + 1 = 2 + 3 -> v[5] - v[5 - k] = v[5 + k] - v[5]
k = 3
1 + 2 + 3 = 4 + 1 + 2 -> v[3] - v[3 - k] = v[3 + k] - v[3]
2 + 3 + 4 = 1 + 2 + 3 -> v[4] - v[4 - k] = v[4 + k] - v[4]
你有一个 pivot 点 pp 属于范围 [k; v.size() - k)。 您的 lhs 公式是 str 的 substring 的字符之和,索引 pp 左侧有 k 个字符,包括 pp 是 v[pp] - v[pp - k] ,而 rhs 是str 的 substring 在索引 pp 的右侧有 k 个字符,不包括 pp 是 v[pp + k] - v[pp]。 您正在处理 tmp 的 substring 的长度始终为 k * 2 或 k << 1。您必须将 tmp 与 max 进行比较,这是您迄今为止在 v 中处理的最长 substring 的长度,并在需要时将 tmp 分配给 max。 我将每个 v 的最大值存储在一个名为 ans 的向量中,然后将 output 的内容与 std::copy 一起存储。
我试着解决这个问题。 这是一种简单的蛮力方法。 让我解释一下我的代码,以便您了解基本逻辑并可以自己在 c++ 中实现。
伪代码:
从输入数字 (n) 创建一个数字列表 (lst)。这里我使用 map 将字符串转换为 integer 然后将其转换为列表。
创建一个包含列表 (lst) 的所有子字符串的列表 (substr)。
从长度为奇数的列表 (substr) 中删除所有子字符串。 如果长度是奇数,那么我们无法将子字符串分成相等的分区(请参阅问题) 。
然后简单地从列表(substr)中迭代子字符串并分成两个分区(k1和k2)并检查总和是否相等。
如果它们相等,则 append 将以下 substring 的长度放入列表 (fi)。
然后打印存储在列表 (fi) 中的最大长度。
for i in range(int(input())): n = input() lst = list(map(int, n)) substr = [lst[i: j] for i in range(len(lst)) for j in range(i + 1, len(lst) + 1)] for i in substr: if (len(i) % 2:= 0). substr:remove(i) fi = [] for lst1 in substr: mid = int(len(lst1)/2) k1 = lst1[0:mid] k2 = lst1[mid:len(lst1)] if(sum(k1) == sum(k2)). fi:append(len(lst1)) if(len(fi) == 0): print("0") else: print(max(fi))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.