Subversion Repositories Kolibri OS

Rev

Rev 9659 | Rev 9903 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
8728 leency 1
(*
9902 akron1 2
    Copyright 2021-2023 Anton Krotov
8728 leency 3
 
4
    This file is part of CEdit.
5
 
6
    CEdit is free software: you can redistribute it and/or modify
7
    it under the terms of the GNU General Public License as published by
8
    the Free Software Foundation, either version 3 of the License, or
9
    (at your option) any later version.
10
 
11
    CEdit is distributed in the hope that it will be useful,
12
    but WITHOUT ANY WARRANTY; without even the implied warranty of
13
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
    GNU General Public License for more details.
15
 
16
    You should have received a copy of the GNU General Public License
17
    along with CEdit. If not, see .
18
*)
19
 
20
MODULE Search;
21
 
22
IMPORT
23
    CB := Clipboard, List, Utils, SYSTEM;
24
 
25
 
26
TYPE
27
    tBuffer* = CB.tBuffer;
28
 
9902 akron1 29
    tIdxTable = ARRAY 65536, 2 OF INTEGER;
8728 leency 30
 
31
    tPos* = POINTER TO RECORD (List.tItem)
32
        pos*: INTEGER
33
    END;
34
 
9902 akron1 35
VAR
36
	table: POINTER TO RECORD data: tIdxTable END;
8728 leency 37
 
9902 akron1 38
 
39
PROCEDURE _index (text: tBuffer; cs: BOOLEAN; VAR table: tIdxTable): tBuffer;
8728 leency 40
VAR
41
    pChar, cnt, i: INTEGER;
42
    c: WCHAR;
43
    res: tBuffer;
44
BEGIN
45
    pChar := text.dataPtr;
9659 akron1 46
    cnt := CB.bufSize(text) DIV SYSTEM.SIZE(WCHAR);
8728 leency 47
 
48
    FOR i := 0 TO 65535 DO
49
        table[i, 1] := 0
50
    END;
51
 
52
    i := cnt;
53
    WHILE i > 0 DO
54
        SYSTEM.GET(pChar, c);
55
        IF ~cs & Utils.cap(c) THEN
56
            SYSTEM.PUT(pChar, c)
57
        END;
58
        INC(table[ORD(c), 1]);
9659 akron1 59
        INC(pChar, SYSTEM.SIZE(WCHAR));
8728 leency 60
        DEC(i)
61
    END;
62
 
9659 akron1 63
    res := CB.create(cnt*SYSTEM.SIZE(INTEGER));
8728 leency 64
 
65
    table[0, 0] := res.dataPtr;
66
    FOR i := 1 TO 65535 DO
9659 akron1 67
        table[i, 0] := table[i - 1, 0] + table[i - 1, 1]*SYSTEM.SIZE(INTEGER)
8728 leency 68
    END;
69
 
70
    pChar := text.dataPtr;
71
    i := 0;
72
    WHILE i < cnt DO
73
        SYSTEM.GET(pChar, c);
74
        SYSTEM.PUT(table[ORD(c), 0], i);
75
        INC(table[ORD(c), 0], SYSTEM.SIZE(INTEGER));
9659 akron1 76
        INC(pChar, SYSTEM.SIZE(WCHAR));
8728 leency 77
        INC(i)
78
    END;
79
 
80
    FOR i := 0 TO 65535 DO
9659 akron1 81
        DEC(table[i, 0], table[i, 1]*SYSTEM.SIZE(INTEGER))
8728 leency 82
    END
83
 
84
    RETURN res
9902 akron1 85
END _index;
86
 
87
 
88
PROCEDURE index* (text: tBuffer; cs: BOOLEAN): tBuffer;
89
BEGIN
90
	IF table = NIL THEN
91
		NEW(table)
92
	END
93
	RETURN _index(text, cs, table.data)
8728 leency 94
END index;
95
 
96
 
9902 akron1 97
PROCEDURE find* (text: tBuffer; s: ARRAY OF WCHAR; whole: BOOLEAN; list: List.tList);
8728 leency 98
VAR
99
    k, pos, n, x, prev_item_pos: INTEGER;
100
    item: tPos;
101
    c1, c2: WCHAR;
102
    flag: BOOLEAN;
103
BEGIN
9902 akron1 104
	ASSERT(table # NIL);
8728 leency 105
    n := LENGTH(s);
9902 akron1 106
    k := table.data[ORD(s[0]), 1];
107
    pos := table.data[ORD(s[0]), 0];
8728 leency 108
    prev_item_pos := 0;
109
    WHILE k > 0 DO
110
        SYSTEM.GET(pos, x);
9659 akron1 111
        IF Utils.streq(text.dataPtr + x*SYSTEM.SIZE(WCHAR), SYSTEM.ADR(s[0]), n) THEN
8728 leency 112
            flag := whole;
113
            IF flag THEN
114
                IF x > 0 THEN
9659 akron1 115
                    SYSTEM.GET(text.dataPtr + (x - 1)*SYSTEM.SIZE(WCHAR), c1);
8728 leency 116
                ELSE
117
                    c1 := 0X
118
                END;
9659 akron1 119
                SYSTEM.GET(text.dataPtr + (x + n)*SYSTEM.SIZE(WCHAR), c2);
9902 akron1 120
                flag := Utils.isLetter(c1) OR Utils.isLetter(c2) OR Utils.isDigit(c1) OR Utils.isDigit(c2) OR
121
                	(c1 = "_") OR (c2 = "_")
8728 leency 122
            END;
123
            IF ~flag & (x >= prev_item_pos) THEN
124
                prev_item_pos := x + n;
125
                NEW(item);
126
                item.pos := x;
127
                List.append(list, item)
128
            END
129
        END;
130
        INC(pos, SYSTEM.SIZE(INTEGER));
131
        DEC(k)
132
    END
133
END find;
134
 
135
 
9902 akron1 136
PROCEDURE close*;
137
BEGIN
138
	IF table # NIL THEN
139
		DISPOSE(table)
140
	END
141
END close;
142
 
143
 
144
BEGIN
145
	table := NIL
8728 leency 146
END Search.