This commit is contained in:
e2hang
2025-09-29 11:06:08 +08:00
parent 3bde00039c
commit a4ebdcc477
7 changed files with 776 additions and 0 deletions

View File

@@ -0,0 +1,108 @@
#include <iostream>
using namespace std;
template <class T>
struct Node {
T element;
Node<T>* next;
Node(const T& e, Node<T>* n = nullptr) : element(e), next(n) {}
};
template <class T>
class Chain {
private:
Node<T>* head;
int size;
public:
Chain() : head(nullptr), size(0) {}
~Chain() {
while (head != nullptr) {
Node<T>* tmp = head;
head = head->next;
delete tmp;
}
}
void insert(int pos, const T& e) {
if (pos < 0 || pos > size) {
throw invalid_argument("Invalid insert position");
}
if (pos == 0) {
head = new Node<T>(e, head);
} else {
Node<T>* prev = head;
for (int i = 0; i < pos - 1; i++) {
prev = prev->next;
}
prev->next = new Node<T>(e, prev->next);
}
size++;
}
void erase(int pos) {
if (pos < 0 || pos >= size) {
throw invalid_argument("Invalid erase position");
}
Node<T>* toDelete;
if (pos == 0) {
toDelete = head;
head = head->next;
} else {
Node<T>* prev = head;
for (int i = 0; i < pos - 1; i++) {
prev = prev->next;
}
toDelete = prev->next;
prev->next = toDelete->next;
}
delete toDelete;
size--;
}
void print() const {
Node<T>* cur = head;
while (cur != nullptr) {
cout << cur->element << " ";
cur = cur->next;
}
cout << endl;
}
};
int main(){
int n;
cin >> n;
Chain<int> list;
for (int i = 0; i < n; i++) {
int x;
cin >> x;
try {
list.insert(i, x);
}
catch(const invalid_argument& e) {}
}
int m;
cin >> m;
for (int i = 0; i < m; i++) {
int op, k, d;
cin >> op;
if (op == 0) {
cin >> k >> d;
try {
list.insert(k, d);
} catch(const invalid_argument& e) {}
} else if (op == 1) {
cin >> k;
try {
list.erase(k - 1);
} catch(const invalid_argument& e) {}
}
}
list.print();
return 0;
}

View File

@@ -0,0 +1,83 @@
#include <iostream>
#include <limits>
using namespace std;
template <class T>
class Stack {
T* element;
int length;
int stackTop;
const T INF = std::numeric_limits<T>::max();
public:
Stack(int l) {
stackTop = -1;
length = l;
element = new T[l];
}
~Stack() {
delete[] element;
}
T& top() {
if (stackTop == -1) throw std::invalid_argument("No Top Element.");
return element[stackTop];
}
void pop() {
if (stackTop == -1) throw std::invalid_argument("No Top Element.");
stackTop--;
}
void push(const T& e) {
if (stackTop == length - 1) {
T* tmp = new T[2 * length];
for (int i = 0; i < length; i++) {
tmp[i] = element[i];
}
delete[] element;
element = tmp;
length *= 2;
}
stackTop++;
element[stackTop] = e;
}
bool empty() const {
return stackTop == -1;
}
};
int main() {
int n;
cin >> n;
Stack<int> s(n);
for (int i = 0; i < n; i++) {
int p;
cin >> p;
switch (p) {
case 0: {
if (!s.empty()) {
cout << s.top() << endl;
s.pop();
} else {
cout << "invalid" << endl;
}
break;
}
case 1: {
int val;
cin >> val;
s.push(val);
break;
}
default:
return 0;
}
}
return 0;
}

View File

@@ -0,0 +1,94 @@
#include <iostream>
#include <limits>
using namespace std;
template <class T>
class Queue {
private:
T* element;
int begin;
int end;
int capacity;
public:
static constexpr T INF = numeric_limits<T>::max();
Queue(int len) : begin(0), end(0), capacity(len) {
element = new T[len];
}
~Queue() {
delete[] element;
}
void push(const T& e) {
if (end == capacity) {
int newCap = capacity * 2;
T* tmp = new T[newCap];
for (int i = begin; i < end; i++) {
tmp[i - begin] = element[i];
}
end -= begin;
begin = 0;
capacity = newCap;
delete[] element;
element = tmp;
}
element[end++] = e;
}
void pop() {
if (empty()) throw std::invalid_argument("Queue is empty.");
begin++;
}
T& front() {
if (empty()) throw std::invalid_argument("Queue is empty.");
return element[begin];
}
T& back() {
if (empty()) throw std::invalid_argument("Queue is empty.");
return element[end - 1];
}
bool empty() const {
return begin == end;
}
int size() const {
return end - begin;
}
};
int main() {
int n;
cin >> n;
Queue<int> q(n);
for (int i = 0; i < n; i++) {
int p;
cin >> p;
switch (p) {
case 0: {
if (q.empty()) {
cout << "invalid" << endl;
} else {
cout << q.front() << endl;
q.pop();
}
break;
}
case 1: {
int val;
cin >> val;
q.push(val);
break;
}
default: {
return 0;
}
}
}
return 0;
}

View File

@@ -0,0 +1,71 @@
#include <iostream>
#include <string>
#include <vector>
using namespace std;
vector<int> build_next(const string& p) {
int n = p.size(); // 模式串长度
vector<int> nxt(n, 0); // 存放 next 数组,初始化全 0
for (int i = 1, j = 0; i < n; i++) {
// --- step1: 如果当前字符不匹配,回退 j ---
while (j > 0 && p[i] != p[j])
j = nxt[j - 1]; // j 回退到上一个最长前后缀的长度,采用动态规划思想
// --- step2: 如果匹配成功j 前进 ---
if (p[i] == p[j])
j++;
// --- step3: 记录当前前缀的 next 值 ---
nxt[i] = j; // 表示 p[0..i] 的最长公共前后缀长度
}
return nxt;
}
vector<int> next_arr(const string& x) {
int n = x.size();
vector<int> tmp(n, 0);
for (int i = 0; i < n; i++) {
int j = 0;
for (int len = i; len > 0; len--) {
if (x.substr(0, len) == x.substr(i - len + 1, len)) {
j = len;
break;
}
}
tmp[i] = j;
}
return tmp;
}
int main(){
string mod, input;
cin >> input >> mod;
vector<int> next = build_next(mod);
int n = mod.size();
int pi = 0, pm = 0;
cout << next[n / 4] << " " << next[n / 2] << " " << next[3 * n / 4] << endl;
while (pi < input.size()) {
if (input[pi] == mod[pm]) {
pi++;
pm++;
if (pm == mod.size()) {
cout << pi - pm << " "; // 匹配位置(起始下标)
return 0;
pm = next[pm - 1]; // 回退
}
} else {
if (pm > 0)
pm = next[pm - 1]; // 回退
else
pi++;
}
}
cout << -1 << endl;
return 0;
}
qwerababcabcabcabcdaabcabhlk

View File

@@ -0,0 +1,167 @@
``` html
A 单链表基本操作
分数 10
作者 朱允刚
单位 吉林大学
请编写程序实现单链表插入、删除结点等基本算法。给定一个单链表和一系列插入、删除结点的操作序列,输出实施上述操作后的链表。单链表数据域值为整数。
输入格式:
输入第1行为1个正整数n表示当前单链表长度第2行为n个空格间隔的整数为该链表n个元素的数据域值。第3行为1个正整数m表示对该链表施加的操作数量接下来m行每行表示一个操作为2个或3个整数格式为0 k d或1 k。0 k d表示在链表第k个结点后插入一个数据域值为d的结点若k=0则表示表头插入。1 k表示删除链表中第k个结点此时k不能为0。注操作序列中若含有不合法的操作如在长度为5的链表中删除第8个结点、删除第0个结点等则忽略该操作。n和m不超过100000。
输出格式:
输出为一行整数表示实施上述m个操作后的链表每个整数后一个空格。输入数据保证结果链表不空。
输入样例:
5
1 2 3 4 5
5
0 2 8
0 9 6
0 0 7
1 0
1 6
输出样例:
7 1 2 8 3 5
代码长度限制
16 KB
Python (python3)
时间限制
1000 ms
内存限制
256 MB
Java (javac)
时间限制
5000 ms
内存限制
256 MB
其他编译器
时间限制
100 ms
内存限制
10 MB
栈限制
8192 KB
---
B 栈的实现及基本操作
分数 10
作者 朱允刚
单位 吉林大学
给定一个初始为空的栈和一系列压栈、弹栈操作请编写程序输出每次弹栈的元素。栈的元素值均为整数。本题不允许使用stack、queue、vector等STL容器。
输入格式:
输入第1行为1个正整数n表示操作个数接下来n行每行表示一个操作格式为1 d或0。1 d表示将整数d压栈0表示弹栈。n不超过20000。
输出格式:
按顺序输出每次弹栈的元素每个元素一行。若某弹栈操作不合法如在栈空时弹栈则对该操作输出invalid。
输入样例:
7
1 1
1 2
0
0
0
1 3
0
输出样例:
2
1
invalid
3
代码长度限制
16 KB
时间限制
50 ms
内存限制
10 MB
栈限制
131000 KB
---
C 队列的实现及基本操作
分数 10
作者 朱允刚
单位 吉林大学
给定一个初始为空的队列和一系列入队、出队操作,请编写程序输出每次出队的元素。队列的元素值均为整数。
备注本题不允许使用stack、queue、vector等STL容器。
输入格式:
输入第1行为1个正整数n表示操作个数接下来n行每行表示一个操作格式为1 d或0。1 d表示将整数d入队0表示出队。n不超过20000。
输出格式:
按顺序输出每次出队的元素每个元素一行。若某出队操作不合法如在队列空时出队则对该操作输出invalid。
输入样例:
7
1 1
1 2
0
0
0
1 3
0
输出样例:
1
2
invalid
3
代码长度限制
16 KB
时间限制
50 ms
内存限制
20 MB
栈限制
8192 KB
---
D KMP模式匹配算法
分数 10
作者 朱允刚
单位 吉林大学
给定目标串s和模式串p编写程序使用KMP算法进行模式匹配计算p在s中首次出现的位置若p不在s中则输出1。字符串下标从0开始。
输入格式:
输入为2行第1行为主串s第2行为模式串p。主串和模式串长度不超过10
5
输出格式:
输出为2行第1行为3个整数表示分别在模式串p的p
m/4
,p
2m/4
,p
3m/4
处失配后模式串下一次匹配的位置即next[j]或f[j1]+1的值j=m/4,2m/4,3m/4每个整数后一个空格m表示模式串p的长度第2行为一个整数表示p在s中首次出现的位置若p不在s中则输出1。
输入样例:
qwerababcabcabcabcdaabcabhlk
abcabcabcabc
输出样例:
0 3 6
6
代码长度限制
16 KB
时间限制
20 ms
内存限制
10 MB
栈限制
8192 KB
```