-
-
Notifications
You must be signed in to change notification settings - Fork 9
/
Copy pathutil.gd
97 lines (80 loc) · 2.88 KB
/
util.gd
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
extends Object
## Utility functions
static func bbcode_escape(p_text: String) -> String:
return p_text \
.replace("[", "~LB~") \
.replace("]", "~RB~") \
.replace("~LB~", "[lb]") \
.replace("~RB~", "[rb]")
static func bbcode_strip(p_text: String) -> String:
var stripped := ""
var in_brackets: bool = false
for c: String in p_text:
if c == '[':
in_brackets = true
elif c == ']':
in_brackets = false
elif not in_brackets:
stripped += c
return stripped
static func get_method_info(p_callable: Callable) -> Dictionary:
var method_info: Dictionary
var method_list: Array[Dictionary]
if p_callable.get_object() is GDScript:
method_list = p_callable.get_object().get_script_method_list()
else:
method_list = p_callable.get_object().get_method_list()
for m in method_list:
if m.name == p_callable.get_method():
method_info = m
break
return method_info
## Finds the most similar string in an array.
static func fuzzy_match_string(p_string: String, p_max_edit_distance: int, p_array) -> String:
if typeof(p_array) < TYPE_ARRAY:
push_error("LimboConsole: Internal error: p_array is not an array")
return ""
if p_array.size() == 0:
return ""
var best_distance: int = 9223372036854775807
var best_match: String = ""
for i in p_array.size():
var elem := str(p_array[i])
var dist: float = _calculate_osa_distance(p_string, elem)
if dist < best_distance:
best_distance = dist
best_match = elem
return best_match if best_distance <= p_max_edit_distance else ""
## Calculates optimal string alignment distance [br]
## See: https://en.wikipedia.org/wiki/Levenshtein_distance
static func _calculate_osa_distance(s1: String, s2: String) -> int:
var s1_len: int = s1.length()
var s2_len: int = s2.length()
# Iterative approach with 3 matrix rows.
# Most of the work is done on row1 and row2 - row0 is only needed to calculate transposition cost.
var row0: PackedInt32Array # previous-previous
var row1: PackedInt32Array # previous
var row2: PackedInt32Array # current aka the one we need to calculate
row0.resize(s2_len + 1)
row1.resize(s2_len + 1)
row2.resize(s2_len + 1)
# edit distance is the number of characters to insert to get from empty string to s2
for i in range(s2_len + 1):
row1[i] = i
for i in range(s1_len):
# edit distance is the number of characters to delete from s1 to match empty s2
row2[0] = i + 1
for j in range(s2_len):
var deletion_cost: int = row1[j + 1] + 1
var insertion_cost: int = row2[j] + 1
var substitution_cost: int = row1[j] if s1[i] == s2[j] else row1[j] + 1
row2[j + 1] = min(deletion_cost, insertion_cost, substitution_cost)
if i > 1 and j > 1 and s1[i - 1] == s2[j] and s1[i - 1] == s2[j]:
var transposition_cost: int = row0[j - 1] + 1
row2[j + 1] = mini(transposition_cost, row2[j + 1])
# Swap rows.
var tmp: PackedInt32Array = row0
row0 = row1
row1 = row2
row2 = tmp
return row1[s2_len]