Pagini recente » runda/preoni2007_runda4_1112 | Cod sursa (job #1527092)
#include <fstream>
#include <vector>
#include <iostream>
// c u l s i u a a v o m n e w d h h x q q p m b o p i h m w d r h n x a g y g j y b c c u l s i uaavomnculsiuaavculsiuaavomculsiuaavomnewdhhx
//-1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1
std::vector<int> first_occurence(const std::string &data, const std::string &key)
{
std::vector<int> v(key.size() + 1);
v[0] = -1, v[1] = 0;
std::vector<int> ret;
for (unsigned i = 1; i < v.size() - 1; i++)
if (key[i] == key[v[i]])
v[i + 1] = v[i] + 1;
else
if (v[v[i]] >= 0 && key[v[v[i]]] == key[i])
v[i + 1] = v[v[i]] + 1;
else
v[i + 1] = 0;
//for (unsigned ii = 0; ii < v.size(); ii++)
// std::cout << v[ii] << ' ';
//std::cout << '\n';
unsigned it1 = 0, it2 = 0;
while (it1 < data.size())
{
if (data[it1] == key[it2])
{
it1++, it2++;
if (it2 == key.size())
{
ret.push_back(it1 - key.size());
it2 = v[it2];
}
continue;
}
it2 = v[it2] < 0 ? it1++, 0 : v[it2];
}
return ret;
}
std::vector<int> first_occurence2(const std::string &data, const std::string &key)
{
int i = 0, k = 0, n, m, t = 0;
std::vector<int> ret, pmt(key.size() + 1, 0);
m = key.size();
n = data.size();
pmt[0] = -1;
k = 2;
while (k <= m)
{
while (key[k - 1] == key[t])
pmt[k++] = ++t;
if (t)
t = pmt[t];
else
pmt[k++] = 0;
}
//for (unsigned ii = 0; ii < pmt.size(); ii++)
// std::cout << pmt[ii] << ' ';
//std::cout << '\n';
k = 0;
while (k + i < n)
{
while (key[i] == data[k + i] && i < m)
i++;
if (i == m)
ret.push_back(k);
k += i - pmt[i];
if (pmt[i] > -1)
i = pmt[i];
else
i = 0;
}
return ret;
}
int main()
{
std::ifstream in("strmatch.in");
std::ofstream out("strmatch.out");
std::string data, key;
in >> key >> data;
auto ret = first_occurence(data, key);
//ret = first_occurence2(data, key);
out << ret.size() << '\n';
int s = std::min(1000, static_cast<int>(ret.size()));
for (int i = 0; i < s; i++)
out << ret[i] << ' ';
out << '\n';
}