-
Notifications
You must be signed in to change notification settings - Fork 1
/
searchmodels.py
170 lines (147 loc) · 6.25 KB
/
searchmodels.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
import json
import sys
class _Options:
def __init__(self):
self.values = tuple() # options with non-Boolean values (strings or numbers)
self.flags = tuple() # Boolean options
self.parameters = []
self.parameters_cursor = 0
def set_values(self, *values):
self.values = [value.lower() for value in values]
for option in self.values:
vars(self)[option] = None
def set_flags(self, *flags):
self.flags = [flag.lower() for flag in flags]
for option in self.flags:
vars(self)[option] = False
def get(self, name):
return vars(self)[name]
def consume_parameter(self):
if self.parameters_cursor < len(self.parameters):
parameter = self.parameters[self.parameters_cursor]
self.parameters_cursor += 1
return parameter
else:
return None
def parse(self, args):
for arg in args:
if arg[0] == '-':
t = arg[1:].split('=', 1)
t[0] = t[0].replace("-", "_")
if len(t) == 1:
flag = t[0].lower()
if flag in self.flags:
vars(self)[flag] = True
assert flag not in self.values or flag == 'dataexport', "You have to specify a value for the option -" + flag
else:
print("Warning: the " + arg + " option is not an option.")
else:
assert len(t) == 2
value = t[0].lower()
if value in self.values:
assert len(t[1]) > 0, "The value specified for the option -" + value + " is the empty string"
vars(self)[value] = t[1]
else:
print("Warning: the " + arg + " option is not an option.")
sys.exit(1)
else:
self.parameters.append(arg)
if __name__ == '__main__':
Options = _Options()
Options.set_values("constraint", "tag", "name")
Options.set_flags("cop", "csp", "reverse", "json", "github", "dir", "help", "showtags", "showconstraints")
Options.parse(sys.argv)
if len(sys.argv) == 1 or (Options.csp and Options.cop) or (Options.json and Options.github):
print("usage: python searchmodels.py [-constraint=Sum] [-tag=xcsp23] [-name='Bacp*'] [-cop|csp] [-reverse] [-json|-dir|-github] [-showtags] [-showcontraints]")
sys.exit(1)
if Options.help :
print("usage: python searchmodels.py [-constraint=Sum] [-tag=xcsp23] [-name='Bacp'] [-cop|csp] [-reverse] [-json|-dir] [-showtags] [-showcontraints]")
print()
print("Extract problems with respect to a given query. You can mix different queries resulting to all problems that matches all queries. You can also reverse the results.")
print()
print(" -help display this help and exit")
print(" -showtags show all available tags")
print(" -showconstraints show all available constraints")
print()
print(" -constraint=Sum extract all problems with Sum constraint")
print(" -tag=xcsp2 extract all problems with tag containing xcsp2 (xcsp22, xcsp23...)")
print(" -name=Ba extract all problems containing BA as a substring")
print(" -cop|-csp extract cop or csp problems")
print(" -reverse reverse the results")
print()
print(" -json display results as a json file")
print(" -github display results as links to github project\n")
print(" -dir display results as directory location\n")
sys.exit(1)
results = []
constraints = []
problems = []
tags = []
csp = []
cop = []
models = json.load(open("_private/models.json"))
if Options.showtags:
tags = {}
for model in models:
for t in model['tags']:
if t not in tags.keys():
tags[t] = 1
print(" ".join(tags.keys()))
sys.exit()
if Options.showconstraints:
constraints = {}
for model in models:
for c in model['constraints']:
if c not in constraints.keys():
constraints[c] = 1
print(" ".join(constraints.keys()))
sys.exit()
for model in models:
if Options.constraint is not None:
constraints.extend([model['name'] for c in model['constraints'] if c == Options.constraint])
if Options.tag is not None:
tags.extend([model['name'] for t in model['tags'] if Options.tag.upper() in t.upper()])
if Options.name is not None and Options.name.upper() in model['name'].upper():
problems.append(model['name'])
if Options.csp and model['type'] == "CSP":
csp.append(model['name'])
if Options.cop and model['type'] == "COP":
cop.append(model['name'])
# Init results
if Options.constraint is not None :
results = constraints
elif Options.name is not None :
results = problems
elif Options.tag is not None :
results = tags
elif Options.csp:
results = csp
elif Options.cop:
results = cop
# get intersction of filters
if Options.constraint is not None :
results = [r for r in results if r in constraints]
if Options.name is not None :
results = [r for r in results if r in problems]
if Options.tag is not None :
results = [r for r in results if r in tags]
if Options.csp :
results = [r for r in results if r in csp]
if Options.cop :
results = [r for r in results if r in cop]
if Options.reverse :
allmodels = [model['name'] for model in models]
results = [m for m in allmodels if m not in results]
if Options.json :
tmp = [model for model in models if model['name'] in results]
print(json.dumps(tmp, indent=2))
elif Options.github:
for model in models:
if model['name'] in results:
print("https://github.com/xcsp3team/pycsp3-models//tree/main/" + model['fullname'])
elif Options.dir:
for model in models:
if model['name'] in results:
print(model['fullname'])
else:
print(" ".join(results))