Skip to content

Commit d2fb0b6

Browse files
committed
Quantifiers. Implemented ++?? support for ranges:
* `++??` (2 - 4) * `+???` (1 - 4) * `+++?` (3 - 4) * `+?` (1 - 2) etc.
1 parent e051fef commit d2fb0b6

6 files changed

Lines changed: 138 additions & 9 deletions

File tree

regXwild/core/ESS/AlgorithmEss.cpp

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,11 @@ bool AlgorithmEss::search(const tstring& text, const tstring& filter, bool ignor
117117
if(rewindToNextBlock(it)){ continue; } return false;
118118
}
119119

120+
// ++??
121+
if(item.mask.prev & MORE && item.mask.curr & ONE) {
122+
item.gapms = item.overlay + 1;
123+
}
124+
120125
// Sequential combinations of #, ?, +
121126
if((item.mask.curr & SINGLE && item.mask.prev & SINGLE)
122127
|| (item.mask.curr & ONE && item.mask.prev & ONE)
@@ -211,8 +216,10 @@ bool AlgorithmEss::search(const tstring& text, const tstring& filter, bool ignor
211216
}
212217

213218
item.pos = item.left;
214-
if(item.mask.curr & SPLIT) {
219+
if(item.mask.curr & SPLIT)
220+
{
215221
words.left = 0;
222+
item.gapms = 0;
216223
item.mask.prev = BOL;
217224
continue; //to next block
218225
}
@@ -253,6 +260,27 @@ bool AlgorithmEss::search(const tstring& text, const tstring& filter, bool ignor
253260

254261
udiff_t AlgorithmEss::interval()
255262
{
263+
// ++??
264+
if(item.mask.prev & ONE && item.gapms > 0)
265+
{
266+
size_t len = item.prev.length();
267+
diff_t delta = words.found - words.left;
268+
269+
diff_t min = item.gapms;
270+
diff_t max = min + item.overlay + 1;
271+
272+
if(delta < min || delta > max) {
273+
return tstring::npos;
274+
}
275+
276+
if(_text.substr(words.found - len - delta, len).compare(item.prev) == 0) {
277+
return words.found;
278+
}
279+
280+
return tstring::npos;
281+
282+
}
283+
256284
// "#"
257285
if(item.mask.prev & SINGLE)
258286
{

regXwild/core/ESS/AlgorithmEss.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -90,18 +90,19 @@ namespace net { namespace r_eg { namespace regXwild { namespace core { namespace
9090
udiff_t delta;
9191
Mask mask;
9292
unsigned short int overlay;
93+
unsigned short int gapms; // ++??
9394

9495
/** enough of this.. */
9596
tstring prev;
9697

9798
void reset()
9899
{
99-
pos = left = delta = overlay = 0;
100+
pos = left = delta = overlay = gapms = 0;
100101
mask.curr = mask.prev = BOL;
101102
curr.clear();
102103
prev.clear();
103104
};
104-
Item(): pos(0), left(0), delta(0), overlay(0) { };
105+
Item(): pos(0), left(0), delta(0), overlay(0), gapms(0) { };
105106
} item;
106107

107108
/**

regXwildTest/EssRangesTest.cpp

Lines changed: 43 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,14 +15,51 @@ namespace regXwildTest
1515
{
1616
public:
1717

18-
TEST_METHOD(minmaxRangeTest5)
18+
TEST_METHOD(minmaxRangeTest1)
1919
{
20-
tstring filter = _T("year = '##'|year = '####'"); // 2 or 4
20+
tstring filter = _T("'++??'"); // 2-4
2121

22-
Assert::IsTrue(searchEss(_T("year = '2020';"), filter));
23-
Assert::IsTrue(searchEss(_T("year = '20';"), filter));
24-
Assert::IsFalse(searchEss(_T("year = '2020y';"), filter));
25-
Assert::IsFalse(searchEss(_T("year = 2020;"), filter));
22+
Assert::IsFalse(searchEss(_T("number = '';"), filter));
23+
Assert::IsFalse(searchEss(_T("number = '1';"), filter));
24+
Assert::IsTrue(searchEss(_T("number = '12';"), filter));
25+
Assert::IsTrue(searchEss(_T("number = '123';"), filter));
26+
Assert::IsTrue(searchEss(_T("number = '1234';"), filter));
27+
Assert::IsFalse(searchEss(_T("number = '12345';"), filter));
28+
}
29+
30+
TEST_METHOD(minmaxRangeTest2)
31+
{
32+
tstring filter = _T("= '+++??'"); // 3-5
33+
34+
Assert::IsFalse(searchEss(_T("number = '';"), filter));
35+
Assert::IsFalse(searchEss(_T("number = '1';"), filter));
36+
Assert::IsFalse(searchEss(_T("number = '12';"), filter));
37+
Assert::IsTrue(searchEss(_T("number = '123';"), filter));
38+
Assert::IsTrue(searchEss(_T("number = '1234';"), filter));
39+
Assert::IsTrue(searchEss(_T("number = '12345';"), filter));
40+
Assert::IsFalse(searchEss(_T("number = '123456';"), filter));
41+
Assert::IsFalse(searchEss(_T("number = '1234567';"), filter));
42+
}
43+
44+
TEST_METHOD(minmaxRangeTest3)
45+
{
46+
tstring filter = _T("= '+?'"); // 1-2
47+
48+
Assert::IsFalse(searchEss(_T("number = '';"), filter));
49+
Assert::IsTrue(searchEss(_T("number = '1';"), filter));
50+
Assert::IsTrue(searchEss(_T("number = '12';"), filter));
51+
Assert::IsFalse(searchEss(_T("number = '123';"), filter));
52+
}
53+
54+
TEST_METHOD(minmaxRangeTest4)
55+
{
56+
tstring filter = _T("number = '+??';"); // 1-3
57+
58+
Assert::IsFalse(searchEss(_T("number = '';"), filter));
59+
Assert::IsTrue(searchEss(_T("number = '1';"), filter));
60+
Assert::IsTrue(searchEss(_T("number = '12';"), filter));
61+
Assert::IsTrue(searchEss(_T("number = '123';"), filter));
62+
Assert::IsFalse(searchEss(_T("number = '1234';"), filter));
2663
}
2764

2865
TEST_METHOD(rangeAtOneTest1)

regXwildTest/EssSplitTest.cpp

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
#include "stdafx.h"
2+
#include "CppUnitTest.h"
3+
4+
#include "..\regXwild\regXwildAPI.h"
5+
6+
using namespace Microsoft::VisualStudio::CppUnitTestFramework;
7+
using namespace net::r_eg::regXwild;
8+
9+
10+
namespace regXwildTest
11+
{
12+
namespace regXwild = net::r_eg::regXwild;
13+
14+
TEST_CLASS(EssSplitTest)
15+
{
16+
public:
17+
18+
TEST_METHOD(splitTest1)
19+
{
20+
tstring filter = _T("'##'|'####'");
21+
22+
Assert::IsTrue(searchEss(_T("year = '2020';"), filter));
23+
Assert::IsTrue(searchEss(_T("year = '20';"), filter));
24+
Assert::IsFalse(searchEss(_T("year = '2020y';"), filter));
25+
Assert::IsFalse(searchEss(_T("year = 2020;"), filter));
26+
}
27+
28+
TEST_METHOD(splitTest2)
29+
{
30+
tstring filter = _T("year = '####'|year = '##'");
31+
32+
Assert::IsTrue(searchEss(_T("year = '2020';"), filter));
33+
Assert::IsTrue(searchEss(_T("year = '20';"), filter));
34+
Assert::IsFalse(searchEss(_T("year = '2020y';"), filter));
35+
Assert::IsFalse(searchEss(_T("year = 2020;"), filter));
36+
}
37+
38+
TEST_METHOD(splitTest3)
39+
{
40+
tstring filter = _T("str = '+++?'|str = '????'");
41+
42+
Assert::IsFalse(searchEss(_T("str = '12345'"), filter));
43+
Assert::IsTrue(searchEss(_T("str = '1234'"), filter));
44+
Assert::IsTrue(searchEss(_T("str = '123'"), filter));
45+
Assert::IsTrue(searchEss(_T("str = '12'"), filter));
46+
Assert::IsTrue(searchEss(_T("str = '1'"), filter));
47+
Assert::IsTrue(searchEss(_T("str = ''"), filter));
48+
}
49+
50+
51+
private:
52+
53+
bool searchEss(const tstring& data, const tstring& filter)
54+
{
55+
return regXwild::searchEss(data, filter, true);
56+
}
57+
58+
};
59+
}

regXwildTest/regXwildTest.vcxproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,7 @@
165165
<ItemGroup>
166166
<ClCompile Include="AlgorithmExtTest.cpp" />
167167
<ClCompile Include="EssRangesTest.cpp" />
168+
<ClCompile Include="EssSplitTest.cpp" />
168169
<ClCompile Include="stdafx.cpp">
169170
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
170171
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>

regXwildTest/regXwildTest.vcxproj.filters

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,5 +35,8 @@
3535
<ClCompile Include="EssRangesTest.cpp">
3636
<Filter>Source Files</Filter>
3737
</ClCompile>
38+
<ClCompile Include="EssSplitTest.cpp">
39+
<Filter>Source Files</Filter>
40+
</ClCompile>
3841
</ItemGroup>
3942
</Project>

0 commit comments

Comments
 (0)