数据结构实验之串一:KMP简单应用
int nextt[1000005];
void get_next(char str2[]) {
int len = strlen(str2);
nextt[0] = -1;
int j = -1, i = 0;
while (i < len) {
if (j == -1 || str2[i] == str2[j]) {
i++;
j++;
nextt[i] = j;
} else
j = nextt[j]; // 失配回溯
}
}
int kmp(char str1[], char str2[]) {
get_next(str2);
int len1 = strlen(str1), len2 = strlen(str2);
int i = 0, j = 0;
while (i < len1 && j < len2) {
if (j == -1 || str1[i] == str2[j]) {
i++;
j++;
} else
j = nextt[j]; // 失配回溯
}
if (j >= len2)
return i - len2;
else
return -2;
}
int main() {
char str1[1000005], str2[1000005];
while (~scanf("%s", str1)) {
scanf("%s", str2);
printf("%d\n", kmp(str1, str2) + 1);
}
return 0;
}
数据结构实验之串三:KMP应用
int a[10000001], b[10000001];
int nextt[1000001];
void get_next(int b[], int n) {
nextt[0] = -1;
int j = -1, i = 0;
while (i < n) {
if (j == -1 || b[i] == b[j]) {
i++;
j++;
nextt[i] = j;
} else
j = nextt[j]; // 失配回溯
}
}
int kmp(int a[], int b[], int m, int n) {
int i = 0, j = 0;
while (i < m && j < n) {
if (j == -1 || a[i] == b[j]) // j==-1 不能少 因为可能失配回溯到j-1
{
i++;
j++;
} else
j = nextt[j]; // 失配回溯
}
if (j >= n)
return i + 1 - n;
else
return -1;
}
int main() {
int m, n;
scanf("%d", &m);
for (int i = 0; i < m; i++) scanf("%d", &a[i]);
scanf("%d", &n);
for (int i = 0; i < n; i++) scanf("%d", &b[i]);
get_next(b, n);
int ans1 = kmp(a, b, m, n);
if (ans1 == -1)
printf("-1\n");
else {
// 坑点 唯一的确定 不能是两个
int ans2 = kmp(a + ans1, b, m, n); // 二次继续匹配 查看有无二次匹配
if (ans2 == -1)
printf("%d %d\n", ans1, ans1 + n - 1);
else
printf("-1\n");
}
return 0;
}
二叉树的基本操作
using namespace std;
struct node {
char c;
node *l;
node *r;
};
int cnt;
int leaves;
node *init() {
node *tree;
tree = new node;
tree->l = tree->r = NULL;
return tree;
}
node *create(char *s) {
if (s[cnt++] == ',') return NULL;
node *tree = init();
tree->c = s[cnt - 1];
tree->l = create(s);
tree->r = create(s);
return tree;
}
void show_mid(node *root) {
if (root) {
show_mid(root->l);
cout << root->c;
show_mid(root->r);
}
}
void show_back(node *root) {
if (root) {
show_back(root->l);
show_back(root->r);
cout << root->c;
}
}
// 计算叶子的数目
void count_leaves(node *root) {
if (root) {
if (!root->l && !root->r) {
leaves++;
} else {
count_leaves(root->l);
count_leaves(root->r);
}
}
}
// 输出二叉树的子叶
void print_leaves(node *root) {
// 层序遍历原理 从上到下从做到右
// 正好能按相应的的顺序输出 子叶
queue q;
if (root) q.push(root);
while (!q.empty()) {
root = q.front(); //访问队首元素
q.pop(); //删除队首
if (root) {
if (root->l == NULL && root->r == NULL) cout << root->c;
q.push(root->l); // 左子树进入队列
q.push(root->r); // 右子树进入队列
}
}
}
// 层序遍历
void forEach(node *root) // 队列实现
{
queue t;
if (root != NULL) t.push(root);
while (!t.empty()) {
root = t.front();
t.pop();
if (root) {
cout << root->c;
t.push(root->l);
t.push(root->r);
}
}
}
数据结构实验之二叉树六:哈夫曼编码
// A [3345] - 数据结构实验之二叉树六:哈夫曼编码
#include
using namespace std;
int main() {
char s[505];
int cnt[505];
int p[1000];
while (~scanf("%s", s)) {
memset(cnt, 0, sizeof(cnt));
int len = strlen(s);
int sum1 = len * 8;
int sum2 = 0;
for (int i = 0; i < len; i++) cnt[s[i]]++;
int top = 0, down = 0;
for (int i = 0; i < 505; i++) {
if (cnt[i] != 0) p[top++] = cnt[i];
}
sort(p, p + top);
while (top != down) {
int a = p[down++];
if (top != down) {
int b = p[down++];
sum2 += (a + b);
p[top++] = a + b;
sort(p + down, p + top);
}
}
printf("%d %d %.1lf\n", sum1, sum2, sum1 * 1.0 / sum2);
}
return 0;
}
数据结构实验之二叉树一:树的同构
struct tree // 利用静态数组
{
char data;
int l;
int r;
} t1[150], t2[150];
//下面来判断是否为同构
//都为空树,直接返回1;一个空一个不空,直接返回0
//都不空:结点value不同,直接0;结点相同,再看子树
//左子树同不存在,就递归调用右子树
//左子树存在,看是否相等,不相等就交换左右子树,再递归调用
int isok(int a, int b) {
if (a == -1 && b == -1)
return 1;
else if ((a == -1 && b != -1) || (a != -1 && b == -1))
return 0;
else if (t1[a].data != t2[b].data)
return 0;
else if (t1[a].l == -1 && t2[b].l == -1)
return isok(t1[a].r, t2[b].r);
else if (t1[a].l != -1 && t2[b].l != -1 &&
t1[t1[a].l].data == t2[t2[b].l].data)
return (isok(t1[a].l, t2[b].l) && isok(t1[a].r, t2[b].r));
else
return (isok(t1[a].l, t2[b].r) && isok(t1[a].r, t2[b].l));
}
int buildtree(tree tree[], int n) {
int root = -1; // 不初始化会re
char l, r;
if (n) {
int check[150] = {0};
for (int i = 0; i < n; i++) {
cin >> tree[i].data >> l >> r;
if (l != '-') {
tree[i].l = l - '0';
check[tree[i].l] = 1;
} else
tree[i].l = -1;
if (r != '-') {
tree[i].r = r - '0';
check[tree[i].r] = 1;
} else
tree[i].r = -1;
}
for (int i = 0; i < n; i++) {
if (!check[i]) {
root = i;
break;
}
}
}
return root;
}
int main() {
int n, m;
while (cin >> n) {
int a, b;
a = buildtree(t1, n);
cin >> m;
b = buildtree(t2, m);
if (isok(a, b) == 1)
cout << "Yes" << endl;
else
cout << "No" << endl;
}
return 0;
}
先序中序还原 中序后序还原
struct node {
char c;
node *l;
node *r;
};
char s1[55], s2[55];
// 先序中序 还原 s1先序 s2 中序
node *front_mid_create(int len, char *s1, char *s2) {
if (len <= 0) return NULL;
int i;
for (i = 0; i < len; i++) {
if (s2[i] == s1[0]) break;
}
node *tree;
tree = new node;
tree->c = s1[0];
tree->l = front_mid_create(i, s1 + 1, s2);
tree->r = front_mid_create(len - i - 1, s1 + i + 1, s2 + i + 1);
return tree;
}
// 中序后序 还原 s1后序 s2中序
node *mid_back_create(int len, char *s1, char *s2) {
if (len <= 0) return NULL;
int i;
for (i = 0; i < len; i++) {
if (s2[i] == s1[len - 1]) break;
}
node *tree;
tree = new node;
tree->c = s1[len - 1];
tree->l = mid_back_create(i, s1, s2);
tree->r = mid_back_create(len - i - 1, s1 + i, s2 + i + 1);
return tree;
}
int height(node *root) {
if (root) {
int lh = height(root->l);
int rh = height(root->r);
return lh > rh ? lh + 1 : rh + 1;
} else {
return 0;
}
}