source: CIVL/examples/verifyThisProblems/DancingLinks.c@ 2a41e3c

1.23 2.0 main test-branch
Last change on this file since 2a41e3c was f3368e99, checked in by Yihao Yan <yihaoyan1@…>, 10 years ago

formatting some verifyThis problem solutions

git-svn-id: svn://vsl.cis.udel.edu/civl/trunk@3076 fb995dde-84ed-4084-dfe6-e5aef3e2452c

  • Property mode set to 100644
File size: 3.6 KB
Line 
1/**
2@author Yihao Yan
3
4Link(chanllege 3): http://etaps2015.verifythis.org/challenges
5
6problem description:
7Dancing links is a technique introduced in 1979 by Hitotumatu and
8Noshita and later popularized by Knuth. The technique can be used to
9efficiently implement a search for all solutions of the exact cover
10problem, which in its turn can be used to solve Tiling, Sudoku,
11N-Queens, and other problems.
12
13Suppose x points to a node of a doubly linked list; let L[x] and R[x]
14point to the predecessor and successor of that node. Then the operations
15
16L[R[x]] := L[x];
17R[L[x]] := R[x];
18
19remove x from the list. The subsequent operations
20
21L[R[x]] := x;
22R[L[x]] := x;
23
24will put x back into the list again.
25
26command: civl verify -inputN=10 DancingLinks.c
27
28*/
29
30#include <stdlib.h>
31#include <stdbool.h>
32#include <assert.h>
33#include <time.h>
34
35#ifdef _CIVL
36#include <civlc.cvh>
37$input int N=10;
38$assume (N >= 3);
39#else
40int N=10;
41#endif
42
43struct Node{
44 struct Node *left;
45 struct Node *right;
46};
47
48void insert(struct Node *x){
49 x->right->left = x;
50 x->left->right = x;
51}
52
53void delete(struct Node *x){
54 x->right->left = x->left;
55 x->left->right = x->right;
56}
57
58//initilize a linkedlist
59struct Node* init(int n){
60 struct Node *head = (struct Node *)malloc(sizeof(struct Node));
61 struct Node *temp = head;
62
63 temp->left = NULL;
64 while(n > 1){
65 struct Node *new = (struct Node *)malloc(sizeof(struct Node));
66
67 temp->right = new;
68 new->left = temp;
69 temp = temp->right;
70 n--;
71 }
72 temp->right = NULL;
73 return head;
74}
75
76struct Node* getNode(struct Node* list, int index){
77 struct Node *result = list;
78
79 while(index >1){
80 result = result->right;
81 index--;
82 }
83 return result;
84}
85
86void initNodeArray(struct Node** array, struct Node* list, int n){
87 struct Node *cur = list;
88 int index=0;
89
90 while(n > 0){
91 array[index++] = cur;
92 cur = cur->right;
93 n--;
94 }
95}
96
97void verifyDelete(struct Node *list, struct Node **nodeArray, int index, int n){
98 struct Node *temp1 = list;
99
100 for(int i=0; i<index-1; i++){
101 assert(temp1 == nodeArray[i]);
102 assert(temp1->left == (nodeArray[i])->left);
103 if(i != index-2){
104 assert(temp1->right == (nodeArray[i])->right);
105 }else{
106 if(index == n){
107 assert(temp1->right == NULL);
108 }else{
109 assert(temp1->right == nodeArray[index]);
110 }
111 }
112 temp1 = temp1->right;
113 }
114
115 for(int j=index; j<=n-1; j++){
116 assert(temp1 == nodeArray[j]);
117 assert(temp1->right == (nodeArray[j])->right);
118 if(j == index){
119 if(index == 1){
120 assert(temp1->left == NULL);
121 }else{
122 assert(temp1->left == nodeArray[index-2]);
123 }
124 }else{
125 assert(temp1->left == (nodeArray[j])->left);
126 }
127 temp1 = temp1->right;
128 }
129}
130
131void verifyInsert(struct Node *list, struct Node **nodeArray, int index, int n){
132 struct Node *temp1 = list;
133
134 for(int k=0;k < n; k++){
135 assert(temp1 == nodeArray[k]);
136 assert(temp1->left == (nodeArray[k])->left);
137 assert(temp1->right == (nodeArray[k])->right);
138 temp1 = temp1->right;
139 }
140}
141
142int main(){
143 // size of the linked list
144#ifdef _CIVL
145 int n = $choose_int(N-2)+3;
146#else
147 srand(time(NULL));
148 int n = rand()%(N-2)+3;
149#endif
150
151 struct Node *list = init(n);
152 // the index of the node who get deleted
153#ifdef _CIVL
154 int index = $choose_int(n-2)+2;
155#else
156 int index = rand()%(N-2)+2;
157#endif
158
159 struct Node *x = getNode(list, index);
160 struct Node *nodeArray[n];
161
162 initNodeArray(nodeArray, list, n);
163 delete(x);
164 verifyDelete(list, nodeArray, index, n);
165 insert(x);
166 verifyInsert(list, nodeArray, index, n);
167
168 int t = n;
169 struct Node *temp1 = list;
170
171 while(t >0){
172 struct Node *temp2 = temp1;
173
174 temp1 = temp1->right;
175 free(temp2);
176 t--;
177 }
178 return 0;
179}
Note: See TracBrowser for help on using the repository browser.