-
-
Notifications
You must be signed in to change notification settings - Fork 98
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add merge_with()
and intersect_with()
methods to the Array and Dictionary classes
#1756
Comments
I once had a somewhat crazy idea of adding these boolean operation methods to GDScript functions (preferably as an extension to GDScript godotengine/godot#15639, of course). What I say is that
|
I think var dict1 = {a = 1, b = 2}
var dict2 = {b = 3, c = 4}
var dict3 = {b = 2, d = 5}
var dict4 = {c = 4, d = 6}
print(dict1.matching_keys(dict2)) # ["b"]
print(dict1.matching_keys(dict4)) # []
print(dict1.matching_values(dict2)) # []
print(dict1.matching_values(dict3)) # [2]
func get_safely_merged_dict(__dict_a: Dictionary, __dict_b: Dictionary, __matching_values_allowed: bool) -> Dictionary:
var __matching_keys := __dict_a.matching_keys(__dict_b)
if !__matching_keys.empty():
assert(false, str("Dictionaries have matching keys: ", __matching_keys))
var __matching_values := __dict_a.matching_values(__dict_b)
if !__matching_values.empty():
if !__matching_values_allowed:
assert(false, str("Dictionaries have matching values: ", __matching_values))
else:
var __matching_entries := __dict_a.intersect_with(__dict_b)
if !__matching_entries.empty():
assert(false, str("Dictionaries have matching entries: ", __matching_entries))
return __dict_a.merge_with(__dict_b)) |
@Error7Studios You may be right, but remember that var dict1 = {a = 1, b = 2}
var dict2 = {b = 3, c = 4}
var dict3 = {b = 2, d = 5}
print(dict1 & dict2) # {}
print(dict1.keys() & dict2.keys()) # ["b"]
print(dict1 & dict3) # {b: 2}
print(dict1.keys() & dict3.keys()) # ["b"] |
Ah, now I see what you mean by:
That would work, too. |
If we have |
merge_with()
and intersect_with()
methods to the Array and Dictionary classes
Since dictionaries in GDScript preserve the order of elements, it is possible to add an optional var dict1 = {a = 1, b = 2}
var dict2 = {b = 3, c = 4}
print(dict1.merge_with(dict2)) # {a: 1, b: 2, c: 4}
print(dict1.merge_with(dict2, true)) # {a: 1, b: 3, c: 4}
print(dict2.merge_with(dict1)) # {b: 3, c: 4, a: 1}
print(dict2.merge_with(dict1, true)) # {b: 2, c: 4, a: 1} Also, it's not entirely clear what to do if the original arrays contain duplicate elements. [2, 2, 3] | [2, 5] # `[2, 2, 3, 5]` or `[2, 3, 5]`?
[2, 2, 3, 5] & [2, 2] # `[2, 2]` or `[2]`? |
This is my main gripe with this. Those methods make sense in a set, but an array is not a set (that is, it may contain duplicate elements unlike a set). So it's not clear what any of those methods do with duplicates (when the duplicate is on the original). I also think we should have external libraries for those things as these small functions can pile up quite quickly and start becoming bloat if we don't draw a line. |
In such a case, these methods should take this into account. That is, the following option is correct: [2, 2, 3] | [2, 5] # [2, 2, 3, 5]
[2, 2, 3, 5] & [2, 2] # [2, 2] For example, it can be used like this:
In addition, for dictionaries, everything remains in effect, since they do not have the same keys.
Until extensions appear, it will be much less convenient. Also, operator overloading is unlikely to appear in GDScript. |
Related: #867 I personally like the idea of |
I think that |
Set-like operations on arrays (lists) are for example in Haskell (string in Haskell is "array of characters"): >>> "Hello World!" \\ "ell W"
"Hoorld!"
>>> "dog" `union` "cow"
"dogcw"
>>> [1,2,3,4] `intersect` [2,4,6,8]
[2,4] source: https://hackage.haskell.org/package/base-4.16.2.0/docs/Data-List.html#g:20 |
This is already being tracked in #867. |
Yeah, I've seen this proposal.
This may be just a free side effect of Haskell array/string implementation, not a deliberate addition to the language. |
Describe the project you are working on:
A game
Describe the problem or limitation you are having in your project:
Right now, no. But I may need it in the future or someone else needs it now.
See also: godotengine/godot#11073, #1718
Describe the feature / enhancement and how it helps to overcome the problem or limitation:
We can add
merge_with()
andintersect_with()
methods (maybe we need other names) forArray
andDictionary
classes. We can also add operators|
and&
(as shorthand) for these data types.Describe how your proposal will work, with code, pseudocode, mockups, and/or diagrams:
If this enhancement will not be used often, can it be worked around with a few lines of script?:
Maybe. But I think anyone who needs these functions will be happy if these functions are already implemented out of the box.
Is there a reason why this should be core and not an add-on in the asset library?:
This is basic functionality that is also available in some programming languages.
The text was updated successfully, but these errors were encountered: