Cod sursa(job #2166449)

Utilizator AlexnolifeAlexandru Ica Alexnolife Data 13 martie 2018 17:10:23
Problema Potrivirea sirurilor Scor 14
Compilator cpp Status done
Runda Arhiva educationala Marime 1.57 kb
#include <fstream>
#include <string>
#include <array>

void Read(std::string& substring, std::string& fullstring)
{
	std::ifstream f("strmatch.in");

	std::getline(f, substring);
	std::getline(f, fullstring);
}

std::array<int, 1000020U> prefix;

void MakePrefix(const std::string& substring)
{
	size_t i, j = 0U;

	for (i = 1U; i < substring.size();) {
		if (substring[j] == substring[i]) {
			prefix[i] = j + 1;

			++i, ++j;
		}
		else if (j > 0U) {
			j = prefix[j - 1U];
		}
		else {
			prefix[i++] = 0;
		}
	}
}

std::array<size_t, 1010U> index;
size_t lastIndex = 0U;
size_t printSize = 0U;

void KMP(const std::string& substring, const std::string& fullstring)
{
	size_t i, offset = 0U;

	for (i = 0U; i < fullstring.size();) {
		if (substring[offset] != fullstring[i]) { // no matching, start over with searching
			if (offset > 0U)
				offset = prefix[offset - 1U];
			else
				++i;
		}
		else if (substring[offset] == fullstring[i] && offset != substring.size() - 1U) { // characters match but we didn't find the pattern yet
			++i, ++offset;
		}
		else { // we found the match
			lastIndex++;

			if (lastIndex <= 1001U) {
				index[lastIndex] = i - offset;
				printSize = lastIndex;
			}


			if (offset > 0U)
				offset = prefix[offset - 1U];
		}
	}
}

void PrintIndex()
{
	std::ofstream g("strmatch.out");

	g << lastIndex << '\n';

	for (size_t i = 1U; i < printSize; ++i) {
		g << index[i] << ' ';
	}
}

int main(int argc, char * argv[])
{
	std::string fullstring, substring;

	Read(substring, fullstring);
	MakePrefix(substring);
	KMP(substring, fullstring);
	PrintIndex();

	return 0;
}