source: CIVL/examples/verifyThisProblems/lrs.c@ adcb43a

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

format changing

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

  • Property mode set to 100644
File size: 2.8 KB
RevLine 
[724ceb2]1/*
[41eb9b6]2Author: Yihao
[e769359]3
[41eb9b6]4Download LCP.zip from: http://fm2012.verifythis.org/challenges
5
6-----------------
7Problem description:
[724ceb2]8
[e769359]9This is a problem in 2012 as an advance problem for LCP
[724ceb2]10Here is the description:
11Together with a suffix array, LCP can be used to solve interesting text
12problems, such as finding the longest repeated substring (LRS) in a text.
13
14A suffix array (for a given text) is an array of all suffixes of the
15text. For the text [7,8,8,6], the suffix array is
16[[7,8,8,6],
17 [8,8,6],
18 [8,6],
19 [6]]
20
21Typically, the suffixes are not stored explicitly as above but
22represented as pointers into the original text. The suffixes in a suffix
23array are sorted in lexicographical order. This way, occurrences of
24repeated substrings in the original text are neighbors in the suffix
[e769359]25array.
[724ceb2]26
27For the above, example (assuming pointers are 0-based integers), the
28sorted suffix array is:
29[3,0,2,1]
[f7e5282]30
[41eb9b6]31-----------------
32Verification task:
33
34Implement the lrs function, and verify that it behaves in the way described above.
35
[f7e5282]36command: civl verify lrs.c
37
38result: the problem is solved
[724ceb2]39*/
40
[63a79f0]41#include <stdlib.h>
42#include <stdio.h>
43#include <civlc.cvh>
44#include <assert.h>
45
[ae55290]46$input int N_BOUND = 4;
47$input int N;
[63a79f0]48$input int X1[N];
[ae55290]49$assume (N < N_BOUND && N >= 0);
[63a79f0]50
[41eb9b6]51int lcp1(int *arr, int n, int x, int y){
[63a79f0]52 int l=0;
[e769359]53
[63a79f0]54 while (x+l<n && y+l<n && arr[x+l]==arr[y+l]) {
55 l++;
56 }
57 return l;
58}
59
60int compare(int *a, int n, int x, int y) {
61 if (x == y) return 0;
62 int l = 0;
63
64 while (x+l<n && y+l<n && a[x+l] == a[y+l]) {
65 l++;
66 }
67
68 if (x+l == n) return -1;
69 if (y+l == n) return 1;
70 if (a[x+l] < a[y+l]) return -1;
71 if (a[x+l] > a[y+l]) return 1;
72
73 return -2;
74}
75
76void sort(int *a, int n, int *data) {
[41eb9b6]77 for(int i = 0; i < n + 0; i++) {
[63a79f0]78 for(int j = i; j > 0 && compare(a, n, data[j - 1], data[j]) > 0; j--) {
79 int b = j - 1;
80 int t = data[j];
[e769359]81
[63a79f0]82 data[j] = data[b];
83 data[b] = t;
84 }
85 }
86}
87
88int lcp2(int *a, int n, int index, int* suffixes){
89 return lcp1(a,n,suffixes[index], suffixes[index-1]);
90}
91
92/**
93result[0]: index
94result[1]: length
95*/
[41eb9b6]96void lrs(int* a, int n, int *result){
[63a79f0]97 int suffixes[n];
[e769359]98
[41eb9b6]99 for(int i=0; i<n; i++){
[63a79f0]100 suffixes[i] = i;
101 }
102 sort(a, n, suffixes);
[41eb9b6]103 for(int i=1; i<n; i++){
[63a79f0]104 int len = lcp2(a, n, i,suffixes);
[e769359]105
[41eb9b6]106 if(len > result[1]){
[63a79f0]107 result[0] = suffixes[i];
108 result[1] = len;
109 }
110 }
111}
112
113int main(){
114 int* result = (int*)malloc(2* sizeof(int));
[e769359]115
[63a79f0]116 result[0] = 0;
117 result[1] = 0;
118 lrs(X1, N, result);
[e769359]119
[63a79f0]120 int index = result[0];
121 int maxLen = result[1];
[e769359]122
[41eb9b6]123 if(N > 1){
[ae55290]124 $assert($exists {int k | k >= 0 && k <= N - maxLen && k != index}(
125 $forall {i = 0 .. maxLen-1} X1[k+i] == X1[index+i]
[63a79f0]126 ));
[41eb9b6]127 }else{
[ae55290]128 $assert(index == 0 && maxLen == 0);
129 }
[63a79f0]130 free(result);
131 return 0;
132}
Note: See TracBrowser for help on using the repository browser.