summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIdan Horowitz <idan.horowitz@gmail.com>2022-12-01 22:49:50 +0200
committerLinus Groh <mail@linusgroh.de>2022-12-02 13:09:15 +0100
commite29be4eaa82e3868d6bf0f3fab6875a55c455d4e (patch)
tree4fc69f27ac617c5dc1860bd5b050316425bc0ab3
parente359eeabe88ab1d1c932eeab6b04824890e5492f (diff)
downloadserenity-e29be4eaa82e3868d6bf0f3fab6875a55c455d4e.zip
LibJS: Implement Set.prototype.isSubsetOf
-rw-r--r--Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h1
-rw-r--r--Userland/Libraries/LibJS/Runtime/SetPrototype.cpp32
-rw-r--r--Userland/Libraries/LibJS/Runtime/SetPrototype.h1
-rw-r--r--Userland/Libraries/LibJS/Tests/builtins/Set/Set.prototype.isSubsetOf.js8
4 files changed, 42 insertions, 0 deletions
diff --git a/Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h b/Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h
index 0e981d587a..a6d9e47c6a 100644
--- a/Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h
+++ b/Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h
@@ -300,6 +300,7 @@ namespace JS {
P(isPrototypeOf) \
P(isSafeInteger) \
P(isSealed) \
+ P(isSubsetOf) \
P(isView) \
P(isoDay) \
P(isoHour) \
diff --git a/Userland/Libraries/LibJS/Runtime/SetPrototype.cpp b/Userland/Libraries/LibJS/Runtime/SetPrototype.cpp
index 9057d80519..03ee6483b5 100644
--- a/Userland/Libraries/LibJS/Runtime/SetPrototype.cpp
+++ b/Userland/Libraries/LibJS/Runtime/SetPrototype.cpp
@@ -36,6 +36,7 @@ void SetPrototype::initialize(Realm& realm)
define_native_function(realm, vm.names.intersection, intersection, 1, attr);
define_native_function(realm, vm.names.difference, difference, 1, attr);
define_native_function(realm, vm.names.symmetricDifference, symmetric_difference, 1, attr);
+ define_native_function(realm, vm.names.isSubsetOf, is_subset_of, 1, attr);
define_native_accessor(realm, vm.names.size, size_getter, {}, Attribute::Configurable);
define_direct_property(vm.names.keys, get_without_side_effects(vm.names.values), attr);
@@ -439,4 +440,35 @@ JS_DEFINE_NATIVE_FUNCTION(SetPrototype::symmetric_difference)
return result;
}
+// 5 Set.prototype.isSubsetOf ( other ), https://tc39.es/proposal-set-methods/#sec-set.prototype.issubsetof
+JS_DEFINE_NATIVE_FUNCTION(SetPrototype::is_subset_of)
+{
+ // 1. Let O be the this value.
+ // 2. Perform ? RequireInternalSlot(O, [[SetData]]).
+ auto* set = TRY(typed_this_object(vm));
+
+ // 3. Let otherRec be ? GetSetRecord(other).
+ auto other_record = TRY(get_set_record(vm, vm.argument(0)));
+
+ // 4. Let thisSize be the number of elements in O.[[SetData]].
+ auto this_size = set->set_size();
+
+ // 5. If thisSize > otherRec.[[Size]], return false.
+ if (this_size > other_record.size)
+ return false;
+
+ // 6. For each element e of O.[[SetData]], do
+ for (auto& element : *set) {
+ // a. Let inOther be ToBoolean(? Call(otherRec.[[Has]], otherRec.[[Set]], ยซ e ยป)).
+ auto in_other = TRY(call(vm, *other_record.has, other_record.set, element.key)).to_boolean();
+
+ // b. If inOther is false, return false.
+ if (!in_other)
+ return false;
+ }
+
+ // 7. Return true.
+ return true;
+}
+
}
diff --git a/Userland/Libraries/LibJS/Runtime/SetPrototype.h b/Userland/Libraries/LibJS/Runtime/SetPrototype.h
index b5431e23ef..ed0dd74ad9 100644
--- a/Userland/Libraries/LibJS/Runtime/SetPrototype.h
+++ b/Userland/Libraries/LibJS/Runtime/SetPrototype.h
@@ -32,6 +32,7 @@ private:
JS_DECLARE_NATIVE_FUNCTION(intersection);
JS_DECLARE_NATIVE_FUNCTION(difference);
JS_DECLARE_NATIVE_FUNCTION(symmetric_difference);
+ JS_DECLARE_NATIVE_FUNCTION(is_subset_of);
JS_DECLARE_NATIVE_FUNCTION(size_getter);
};
diff --git a/Userland/Libraries/LibJS/Tests/builtins/Set/Set.prototype.isSubsetOf.js b/Userland/Libraries/LibJS/Tests/builtins/Set/Set.prototype.isSubsetOf.js
new file mode 100644
index 0000000000..d5dc6ab9d0
--- /dev/null
+++ b/Userland/Libraries/LibJS/Tests/builtins/Set/Set.prototype.isSubsetOf.js
@@ -0,0 +1,8 @@
+test("basic functionality", () => {
+ expect(Set.prototype.isSubsetOf).toHaveLength(1);
+
+ const set1 = new Set(["a", "b", "c"]);
+ const set2 = new Set(["b", "c"]);
+ expect(set1.isSubsetOf(set2)).toBeFalse();
+ expect(set2.isSubsetOf(set1)).toBeTrue();
+});