P2580 Also hat er den falschen Appell gestartet (Wörterbuchbaum)

Themenhintergrund

Der Trainer des Chemiewettbewerbsteams der XS-Mittelschule ist ein Hearthstone-Liebhaber.

Er rollte das Brötchen, während er den Ofenstein knetete, so dass er eines Tages zweimal hintereinander einen bestimmten Klassenkameraden anrief und dann zufällig vom vorbeikommenden Schulleiter entdeckt wurde, und dann aß er Ola Ola Ola (für Einzelheiten). , siehe bitte das abgeschlossene Spiel CON900).

Themenbeschreibung

Danach ernennt Sie der Schulleiter zum Spezialagenten, der jeden Tag seinen Appell aufzeichnet. Der Schulleiter stellt die Anzahl und die Liste der Schüler des Chemiewettbewerbs zur Verfügung und Sie müssen dem Schulleiter mitteilen, ob ihm ein Fehler unterlaufen ist. (Warum halten Sie ihn nicht einfach davon ab, Hearthstone zu spielen?)

Eingabeformat

Die erste Zeile enthält eine Ganzzahl n, die die Anzahl der Personen in der Klasse darstellt.

In den nächsten n Zeilen enthält jede Zeile eine Zeichenfolge, die ihren Namen darstellt (sie unterscheidet sich voneinander und enthält nur Kleinbuchstaben und die Länge überschreitet 5050 nicht).

Zeile n+2 enthält eine Ganzzahl m, die die Anzahl der vom Coach gemeldeten Namen angibt.

In den nächsten m Zeilen enthält jede Zeile eine Zeichenfolge, die den Namen des Trainers darstellt (nur Kleinbuchstaben und die Länge überschreitet 5050 nicht).

Ausgabeformat

Geben Sie für den gemeldeten Namen jedes Trainers eine Zeile aus.

Wenn der Name korrekt ist und es sich um das erste Vorkommen handelt, wird die Ausgabe ausgegeben.  OKWenn der Name falsch ist, wird die Ausgabe ausgegeben  WRONG. Wenn der Name korrekt ist, aber nicht zum ersten Mal vorkommt, wird die Ausgabe ausgegeben  REPEAT.

Eingabe- und Ausgabebeispiele

Geben Sie zum Kopieren #1 ein

5   
a 
b 
c 
ad 
acd 
3 
a 
a 
e

Ausgabe Nr. 1 Kopie

OK, 
WIEDERHOLEN 
SIE FALSCH

Lösung eins:

Verwenden Sie eine STL-Karte

#define _CRT_SECURE_NO_WARNINGS 1
#include<bits/stdc++.h>
using namespace std;
int n;
int main() {
	map<string, int> student;
	string name;
	cin >> n;
	while (n--) {
		cin >> name;
		student[name] = 1;
	}
	int m; cin >> m;
	while (m--) {
		cin >> name;
		if (student[name] == 1) { puts("OK"); student[name] = 2; }
		else if (student[name] == 2) puts("REPEAT");
		else    puts("WRONG");
	}
	return 0;
}

Lösung zwei:

Wörterbuchbaumanwendung:

1. String-Abruf; 2. Worthäufigkeitsstatistik 3. Sortierung nach Wörterbuchreihenfolge 4. Präfixabgleich

#define _CRT_SECURE_NO_WARNINGS 1
#include<bits/stdc++.h>
using namespace std;
const int N = 800000;
struct node {
	bool repeat; // 这个前缀是否重复
	int son[26]; //26个字母
	int num; // 这个前缀出现的次数
}t[N];
int cnt = 1;  // 当前新分配的存储位置,把cnt = 0 留给根节点
void Insert(char* s) {
	int now = 0;
	for (int i = 0; s[i]; i++) {
		int ch = s[i] - 'a';
		if (t[now].son[ch] == 0) {
			t[now].son[ch] = cnt++;
		}
		now = t[now].son[ch];
		t[now].num++;
	}
}
int Find(char* s) {
	int now = 0;
	for (int i = 0; s[i]; i++) {
		int ch = s[i] - 'a';
		if (t[now].son[ch] == 0) return 3;
		now = t[now].son[ch];
	}
	if (t[now].num == 0) return 3; // 这个前缀没有出现过
	if (t[now].repeat == false) {
		t[now].repeat = true;
		return 1;
	}
	return 2;
}
int main() {
	char s[51];
	int n;
	cin >> n;
	while (n--) {
		scanf("%s", s);
		Insert(s);
	}
	int m;
	scanf("%d", &m);
	while (m--) {
		scanf("%s", s);
		int r = Find(s);
		if (r == 1) { puts("OK"); }
		else if (r == 2) { puts("REPEAT");}
		else { puts("WRONG"); }
	}
	return 0;
}

Ich denke du magst

Origin blog.csdn.net/zhi6fui/article/details/128735353
Empfohlen
Rangfolge