Add pset6
This commit is contained in:
parent
d948bc5084
commit
cda2959974
59
semester3/pset6/7-1-朋友圈点赞.c
Normal file
59
semester3/pset6/7-1-朋友圈点赞.c
Normal file
|
@ -0,0 +1,59 @@
|
|||
#include <stdio.h>
|
||||
#define MAXLEN 256
|
||||
#define SIZE 5
|
||||
|
||||
int getDigits(int i) {
|
||||
int count = 0;
|
||||
do {
|
||||
i /= 10;
|
||||
count++;
|
||||
} while (i);
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
// remember to initialize to 0
|
||||
int matrix[SIZE][SIZE] = {};
|
||||
int liked[SIZE][SIZE] = {};
|
||||
|
||||
char buf[MAXLEN];
|
||||
fgets(buf, MAXLEN, stdin);
|
||||
int offset = 0;
|
||||
int src, dist;
|
||||
|
||||
while (sscanf(buf + offset, "%d,%d,", &src, &dist) != EOF) {
|
||||
// printf("%d -> %d\n", src, dist);
|
||||
offset += getDigits(src) + getDigits(dist) + 2;
|
||||
matrix[src][dist] = 1;
|
||||
}
|
||||
|
||||
// calculate likes
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
int count = 0;
|
||||
for (int j = 0; j < SIZE; j++) {
|
||||
if (matrix[i][j] == 1) {
|
||||
if (++count % 2 == 1) {
|
||||
// printf("%d liked %d, count: %d\n", i, j, count);
|
||||
liked[i][j] = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
scanf("%d", &dist);
|
||||
|
||||
int hasLikes = 0;
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
if (liked[i][dist] == 1) {
|
||||
hasLikes = 1;
|
||||
printf("%d,", i);
|
||||
}
|
||||
}
|
||||
|
||||
if (!hasLikes) {
|
||||
printf("-1");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
184
semester3/pset6/7-2-拓扑排序.c
Normal file
184
semester3/pset6/7-2-拓扑排序.c
Normal file
|
@ -0,0 +1,184 @@
|
|||
// NEEDS REWORKING
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#define SIZE 11
|
||||
|
||||
typedef struct listNode {
|
||||
char ID;
|
||||
struct listNode *next;
|
||||
} listNode;
|
||||
|
||||
typedef struct queue {
|
||||
listNode **arr;
|
||||
int back;
|
||||
int front;
|
||||
} queue;
|
||||
|
||||
listNode *newNode(char ID) {
|
||||
listNode *new = malloc(sizeof(listNode));
|
||||
new->ID = ID;
|
||||
new->next = NULL;
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
queue *newQueue() {
|
||||
queue *q = malloc(sizeof(queue));
|
||||
q->arr = malloc(sizeof(listNode *) * SIZE);
|
||||
q->back = 0;
|
||||
q->front = 0;
|
||||
return q;
|
||||
}
|
||||
|
||||
void appendNode(listNode *node, listNode *new) {
|
||||
while (node->next != NULL) {
|
||||
node = node->next;
|
||||
}
|
||||
node->next = new;
|
||||
}
|
||||
|
||||
void push(listNode *li, queue *q) { q->arr[q->back++] = li; }
|
||||
|
||||
int isEmpty(queue *q) { return (q->front == q->back); }
|
||||
|
||||
listNode *getFront(queue *q) { return q->arr[q->front]; }
|
||||
|
||||
void pop(queue *q) {
|
||||
if (!isEmpty(q)) {
|
||||
q->front++;
|
||||
}
|
||||
}
|
||||
|
||||
listNode **makeGraph() {
|
||||
|
||||
listNode **graph = malloc(sizeof(listNode *) * SIZE);
|
||||
|
||||
// initialize graph
|
||||
int count = 0;
|
||||
graph[count++] = newNode('S');
|
||||
for (; count < 10; count++) {
|
||||
graph[count] = newNode(count + 'A' - 1);
|
||||
}
|
||||
graph[count++] = newNode('T');
|
||||
|
||||
appendNode(graph[0], newNode('A'));
|
||||
appendNode(graph[0], newNode('D'));
|
||||
appendNode(graph[0], newNode('G'));
|
||||
|
||||
appendNode(graph[1], newNode('B'));
|
||||
appendNode(graph[1], newNode('E'));
|
||||
|
||||
appendNode(graph[2], newNode('C'));
|
||||
|
||||
appendNode(graph[3], newNode('T'));
|
||||
|
||||
appendNode(graph[4], newNode('A'));
|
||||
appendNode(graph[4], newNode('E'));
|
||||
|
||||
appendNode(graph[5], newNode('C'));
|
||||
appendNode(graph[5], newNode('F'));
|
||||
appendNode(graph[5], newNode('I'));
|
||||
|
||||
appendNode(graph[6], newNode('C'));
|
||||
appendNode(graph[6], newNode('T'));
|
||||
|
||||
appendNode(graph[7], newNode('D'));
|
||||
appendNode(graph[7], newNode('E'));
|
||||
appendNode(graph[7], newNode('H'));
|
||||
|
||||
appendNode(graph[8], newNode('E'));
|
||||
appendNode(graph[8], newNode('I'));
|
||||
|
||||
appendNode(graph[9], newNode('F'));
|
||||
appendNode(graph[9], newNode('T'));
|
||||
|
||||
return graph;
|
||||
}
|
||||
|
||||
int ch2digit(char ch) {
|
||||
if (ch == 'S') {
|
||||
return 0;
|
||||
} else if (ch == 'T') {
|
||||
return 10;
|
||||
} else {
|
||||
return ch - 'A' + 1;
|
||||
}
|
||||
}
|
||||
|
||||
int *getIndegree(listNode **g) {
|
||||
int *inDegree = malloc(sizeof(int) * SIZE);
|
||||
for (int i = 0; i < SIZE; i++) { // init to 0
|
||||
inDegree[i] = 0;
|
||||
}
|
||||
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
listNode *ptr = g[i]->next;
|
||||
while (ptr != NULL) {
|
||||
inDegree[ch2digit(ptr->ID)]++;
|
||||
ptr = ptr->next;
|
||||
}
|
||||
}
|
||||
|
||||
// for (int i = 0; i < SIZE; i++) {
|
||||
// printf("%c: %d\n", g[i]->ID, inDegree[i]);
|
||||
// }
|
||||
|
||||
return inDegree;
|
||||
}
|
||||
|
||||
void topoSort(listNode **g) {
|
||||
queue *q = newQueue();
|
||||
int visited[SIZE] = {};
|
||||
int *inDegree = getIndegree(g);
|
||||
|
||||
for (int count = 0; count < SIZE; count++) {
|
||||
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
if (inDegree[i] == 0 && visited[i] == 0) {
|
||||
// printf("pushing: %c\n", g[i]->ID);
|
||||
push(g[i], q);
|
||||
visited[i] = 1;
|
||||
}
|
||||
}
|
||||
|
||||
listNode *tmp;
|
||||
while (!isEmpty(q)) {
|
||||
tmp = getFront(q);
|
||||
pop(q);
|
||||
printf("%c,", tmp->ID);
|
||||
|
||||
tmp = g[ch2digit(tmp->ID)]->next;
|
||||
while (tmp != NULL) {
|
||||
if (--inDegree[ch2digit(tmp->ID)] == 0 &&
|
||||
visited[ch2digit(tmp->ID)] == 0) {
|
||||
push(tmp, q);
|
||||
visited[ch2digit(tmp->ID)] = 1;
|
||||
}
|
||||
tmp = tmp->next;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void deleteEdge(listNode **g, char src, char dist) {
|
||||
listNode *ptr = g[ch2digit(src)];
|
||||
while (ptr != NULL && ptr->next != NULL) {
|
||||
if (ptr->next->ID == dist) {
|
||||
ptr->next = ptr->next->next;
|
||||
}
|
||||
ptr = ptr->next;
|
||||
}
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
queue *q = newQueue();
|
||||
listNode **g = makeGraph();
|
||||
|
||||
char src, dist;
|
||||
scanf("%c,%c", &src, &dist);
|
||||
deleteEdge(g, src, dist);
|
||||
|
||||
topoSort(g);
|
||||
|
||||
return 0;
|
||||
}
|
122
semester3/pset6/7-3-Shortest-Path.c
Normal file
122
semester3/pset6/7-3-Shortest-Path.c
Normal file
|
@ -0,0 +1,122 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#define SIZE 7
|
||||
#define MAX 100
|
||||
|
||||
typedef struct node {
|
||||
int index,
|
||||
dist; // for the starting node, dist means shortest distance from start to
|
||||
// here, for child nodes, dist means dist(parent, this)
|
||||
struct node *next;
|
||||
struct node *parent;
|
||||
} node;
|
||||
|
||||
node *newNode(int index, int dist) {
|
||||
node *new = malloc(sizeof(node));
|
||||
new->index = index;
|
||||
new->dist = dist;
|
||||
new->next = NULL;
|
||||
new->parent = NULL;
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
void appendEdge(node *src, int index, int dist) {
|
||||
node *end = newNode(index, dist);
|
||||
node *ptr = src;
|
||||
while (ptr->next != NULL) {
|
||||
ptr = ptr->next;
|
||||
}
|
||||
ptr->next = end;
|
||||
}
|
||||
|
||||
node **makeGraph() {
|
||||
node **g = malloc(sizeof(node *) * SIZE);
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
g[i] = newNode(i, MAX);
|
||||
}
|
||||
appendEdge(g[0], 1, 2);
|
||||
appendEdge(g[0], 3, 1);
|
||||
|
||||
appendEdge(g[1], 3, 3);
|
||||
appendEdge(g[1], 4, 10);
|
||||
|
||||
appendEdge(g[2], 0, 4);
|
||||
appendEdge(g[2], 5, 5);
|
||||
|
||||
appendEdge(g[3], 2, 2);
|
||||
appendEdge(g[3], 4, 2);
|
||||
appendEdge(g[3], 5, 8);
|
||||
appendEdge(g[3], 6, 4);
|
||||
|
||||
appendEdge(g[4], 6, 6);
|
||||
|
||||
appendEdge(g[6], 5, 1);
|
||||
return g;
|
||||
}
|
||||
|
||||
int getMinDistance(node **graph, int visited[]) {
|
||||
int min = MAX, minIndex;
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
if (graph[i]->dist < min && visited[i] == 0) {
|
||||
min = graph[i]->dist;
|
||||
minIndex = i;
|
||||
}
|
||||
}
|
||||
return minIndex;
|
||||
}
|
||||
|
||||
void dijkstra(node **graph, int start) {
|
||||
int visited[SIZE] = {};
|
||||
for (int i = 0; i < SIZE; i++) {
|
||||
int s = getMinDistance(graph, visited);
|
||||
// printf("found start: %d\n", s);
|
||||
|
||||
visited[s] = 1;
|
||||
|
||||
node *ptr = graph[s]->next;
|
||||
|
||||
// update distance of unvisited nodes
|
||||
while (ptr) {
|
||||
if (visited[ptr->index] == 0 &&
|
||||
graph[ptr->index]->dist > ptr->dist + graph[s]->dist) {
|
||||
graph[ptr->index]->dist = ptr->dist + graph[s]->dist;
|
||||
graph[ptr->index]->parent = graph[s];
|
||||
// printf("Updated: %d, dist: %d\n", ptr->index,
|
||||
// graph[ptr->index]->dist);
|
||||
}
|
||||
ptr = ptr->next;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
node **graph = makeGraph();
|
||||
|
||||
int start, end;
|
||||
scanf("%d,%d", &start, &end);
|
||||
start--;
|
||||
end--;
|
||||
|
||||
// init the start's dist as 0
|
||||
graph[start]->dist = 0;
|
||||
dijkstra(graph, start);
|
||||
|
||||
if (graph[end]->parent == NULL) {
|
||||
printf("-1");
|
||||
} else {
|
||||
int route[MAX];
|
||||
int count = 0;
|
||||
node *ptr = graph[end];
|
||||
while (ptr) {
|
||||
route[count++] = ptr->index;
|
||||
ptr = ptr->parent;
|
||||
}
|
||||
|
||||
for (int i = count - 1; i >= 0; i--) {
|
||||
printf("%d,", route[i] + 1);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
Loading…
Reference in a new issue