[libcxx-commits] [libcxx] [libc++][pair] P2944R3: Constrain `std::pair`'s equality operator (PR #136672)

Hristo Hristov via libcxx-commits libcxx-commits at lists.llvm.org
Wed Apr 23 03:24:33 PDT 2025


https://github.com/Zingam updated https://github.com/llvm/llvm-project/pull/136672

>From 12fc4301a288677d4b134be4b0b851bcefba3cd6 Mon Sep 17 00:00:00 2001
From: Hristo Hristov <hghristov.rmm at gmail.com>
Date: Tue, 8 Apr 2025 08:11:51 +0300
Subject: [PATCH 1/6] [libc++][pair] P2944R3: Constrain `pair` equality
 operator

Implements https://wg21.link/P2944R3 (partially):
  - [pairs.spec](https://eel.is/c++draft/pairs.spec)

Related issues:
- Related to #105424
- Related to #118135
---
 libcxx/include/__utility/pair.h               | 10 ++-
 libcxx/include/tuple                          | 11 ++-
 .../size_incompatible_comparison.verify.cpp   |  6 ++
 .../pairs/pairs.spec/comparison.pass.cpp      | 77 +++++++++++++++++++
 4 files changed, 102 insertions(+), 2 deletions(-)

diff --git a/libcxx/include/__utility/pair.h b/libcxx/include/__utility/pair.h
index 1f596a87f7cc7..72363cac9ebec 100644
--- a/libcxx/include/__utility/pair.h
+++ b/libcxx/include/__utility/pair.h
@@ -11,6 +11,7 @@
 
 #include <__compare/common_comparison_category.h>
 #include <__compare/synth_three_way.h>
+#include <__concepts/boolean_testable.h>
 #include <__concepts/different_from.h>
 #include <__config>
 #include <__cstddef/size_t.h>
@@ -447,7 +448,14 @@ pair(_T1, _T2) -> pair<_T1, _T2>;
 
 template <class _T1, class _T2, class _U1, class _U2>
 inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
-operator==(const pair<_T1, _T2>& __x, const pair<_U1, _U2>& __y) {
+operator==(const pair<_T1, _T2>& __x, const pair<_U1, _U2>& __y)
+#if _LIBCPP_STD_VER >= 26
+  requires requires {
+    { __x.first == __y.first } -> __boolean_testable;
+    { __x.second == __y.second } -> __boolean_testable;
+  }
+#endif
+{
   return __x.first == __y.first && __x.second == __y.second;
 }
 
diff --git a/libcxx/include/tuple b/libcxx/include/tuple
index e284f71200492..406feb90fcc51 100644
--- a/libcxx/include/tuple
+++ b/libcxx/include/tuple
@@ -216,6 +216,7 @@ template <class... Types>
 #  include <__compare/common_comparison_category.h>
 #  include <__compare/ordering.h>
 #  include <__compare/synth_three_way.h>
+#  include <__concepts/boolean_testable.h>
 #  include <__config>
 #  include <__cstddef/size_t.h>
 #  include <__fwd/array.h>
@@ -1160,8 +1161,16 @@ struct __tuple_equal<0> {
 
 template <class... _Tp, class... _Up>
 inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
-operator==(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) {
+operator==(const tuple<_Tp...>& __x, const tuple<_Up...>& __y)
+#    if _LIBCPP_STD_VER >= 26
+  requires requires {
+    { sizeof...(_Tp) == sizeof...(_Up) } -> __boolean_testable;
+  }
+#    endif
+{
+#    if _LIBCPP_STD_VER < 26
   static_assert(sizeof...(_Tp) == sizeof...(_Up), "Can't compare tuples of different sizes");
+#    endif
   return __tuple_equal<sizeof...(_Tp)>()(__x, __y);
 }
 
diff --git a/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp b/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
index 851f6fcd1fbac..54936ea535c2b 100644
--- a/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
+++ b/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
@@ -21,9 +21,15 @@
 
 #include <tuple>
 
+#include "test_macros.h"
+
 void f(std::tuple<int> t1, std::tuple<int, long> t2) {
   // We test only the core comparison operators and trust that the others
   // fall back on the same implementations prior to C++20.
+#if TEST_STD_VER >= 26
+  static_cast<void>(t1 == t2);
+#else
   static_cast<void>(t1 == t2); // expected-error@*:* {{}}
+#endif
   static_cast<void>(t1 < t2); // expected-error@*:* {{}}
 }
diff --git a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
index 76f9771f2b99b..da78503abee48 100644
--- a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
+++ b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
@@ -19,9 +19,86 @@
 
 #include <utility>
 #include <cassert>
+#include <concepts>
 
 #include "test_macros.h"
 
+#if TEST_STD_VER >= 26
+
+// template <typename T>
+// class EqualityComparable {
+// public:
+//   constexpr EqualityComparable(T value) : value_{value} {};
+
+//   friend constexpr bool operator==(const EqualityComparable&, const EqualityComparable&) noexcept = default;
+
+// private:
+//   T value_;
+// };
+
+// static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, std::pair<int,int>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>, std::pair<int,int>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, EqualityComparable<std::pair<int,int>>>);
+// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>>);
+// static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, std::pair<int,int>, EqualityComparable<std::pair<int,int>>>);
+// static_assert(EqualityComparable<std::pair<int,int>>{std::pair{94, 82}} == EqualityComparable<std::pair<int,int>>{std::pair{94, 82}});
+// static_assert(EqualityComparable<std::pair<int,int>>{std::pair{94, 82}} != EqualityComparable<std::pair<int,int>>{std::pair{82, 82}});
+
+struct EqualityComparable {
+  constexpr EqualityComparable(int value) : value_{value} {};
+
+  friend constexpr bool operator==(const EqualityComparable&, const EqualityComparable&) noexcept = default;
+
+  int value_;
+};
+
+static_assert(std::equality_comparable<EqualityComparable>);
+static_assert(EqualityComparable{94} == EqualityComparable{94});
+static_assert(EqualityComparable{94} != EqualityComparable{82});
+
+static_assert(std::equality_comparable<std::pair<EqualityComparable, EqualityComparable>>);
+static_assert(std::pair{EqualityComparable{94}, EqualityComparable{94}} ==
+              std::pair{EqualityComparable{94}, EqualityComparable{94}});
+static_assert(std::pair{EqualityComparable{82}, EqualityComparable{94}} !=
+              std::pair{EqualityComparable{94}, EqualityComparable{94}});
+static_assert(std::pair{EqualityComparable{94}, EqualityComparable{82}} !=
+              std::pair{EqualityComparable{94}, EqualityComparable{94}});
+
+struct NonComparable {};
+
+static_assert(!std::three_way_comparable<std::pair<NonComparable, NonComparable>>);
+static_assert(!std::three_way_comparable<std::pair<EqualityComparable, NonComparable>>);
+static_assert(!std::three_way_comparable<std::pair<NonComparable, EqualityComparable>>);
+
+static_assert(!std::equality_comparable<std::pair<EqualityComparable, NonComparable>>);
+static_assert(!std::equality_comparable<std::pair<NonComparable, EqualityComparable>>);
+
+
+template <typename T, typename U>
+concept HasCompare = requires(T t, U u) {
+  { t == u } -> std::same_as<bool>;
+  { t != u } -> std::same_as<bool>;
+  { t < u } -> std::same_as<bool>;
+  { t > u } -> std::same_as<bool>;
+  { t <= u } -> std::same_as<bool>;
+  { t >= u } -> std::same_as<bool>;
+};
+
+template <typename T, typename U>
+concept HasCompare = requires(std::pair p1, std::pair p2) {
+  { t == u } -> std::same_as<bool>;
+  { t != u } -> std::same_as<bool>;
+  { t < u } -> std::same_as<bool>;
+  { t > u } -> std::same_as<bool>;
+  { t <= u } -> std::same_as<bool>;
+  { t >= u } -> std::same_as<bool>;
+};
+
+#endif // TEST_STD_VER >= 26
+
 int main(int, char**)
 {
     {

>From 6d482136c6a064b69f0704a29ed5838d6c6bccbe Mon Sep 17 00:00:00 2001
From: Hristo Hristov <hghristov.rmm at gmail.com>
Date: Fri, 18 Apr 2025 10:51:33 +0300
Subject: [PATCH 2/6] Updated tests

---
 libcxx/docs/Status/Cxx2cPapers.csv            |  2 +-
 libcxx/include/tuple                          | 11 +---
 .../size_incompatible_comparison.verify.cpp   |  6 ---
 .../pairs/pairs.spec/comparison.pass.cpp      | 52 +------------------
 4 files changed, 4 insertions(+), 67 deletions(-)

diff --git a/libcxx/docs/Status/Cxx2cPapers.csv b/libcxx/docs/Status/Cxx2cPapers.csv
index 0cc41d2058dd5..f29de08ba7b5f 100644
--- a/libcxx/docs/Status/Cxx2cPapers.csv
+++ b/libcxx/docs/Status/Cxx2cPapers.csv
@@ -59,7 +59,7 @@
 "`P2248R8 <https://wg21.link/P2248R8>`__","Enabling list-initialization for algorithms","2024-03 (Tokyo)","","",""
 "`P2810R4 <https://wg21.link/P2810R4>`__","``is_debugger_present`` ``is_replaceable``","2024-03 (Tokyo)","","",""
 "`P1068R11 <https://wg21.link/P1068R11>`__","Vector API for random number generation","2024-03 (Tokyo)","","",""
-"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","19","Implemented comparisons for ``reference_wrapper`` only"
+"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","21","Implemented changes to ``reference_wrapper``, ``pair`"
 "`P2642R6 <https://wg21.link/P2642R6>`__","Padded ``mdspan`` layouts","2024-03 (Tokyo)","","",""
 "`P3029R1 <https://wg21.link/P3029R1>`__","Better ``mdspan``'s CTAD","2024-03 (Tokyo)","|Complete|","19",""
 "","","","","",""
diff --git a/libcxx/include/tuple b/libcxx/include/tuple
index 406feb90fcc51..e284f71200492 100644
--- a/libcxx/include/tuple
+++ b/libcxx/include/tuple
@@ -216,7 +216,6 @@ template <class... Types>
 #  include <__compare/common_comparison_category.h>
 #  include <__compare/ordering.h>
 #  include <__compare/synth_three_way.h>
-#  include <__concepts/boolean_testable.h>
 #  include <__config>
 #  include <__cstddef/size_t.h>
 #  include <__fwd/array.h>
@@ -1161,16 +1160,8 @@ struct __tuple_equal<0> {
 
 template <class... _Tp, class... _Up>
 inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
-operator==(const tuple<_Tp...>& __x, const tuple<_Up...>& __y)
-#    if _LIBCPP_STD_VER >= 26
-  requires requires {
-    { sizeof...(_Tp) == sizeof...(_Up) } -> __boolean_testable;
-  }
-#    endif
-{
-#    if _LIBCPP_STD_VER < 26
+operator==(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) {
   static_assert(sizeof...(_Tp) == sizeof...(_Up), "Can't compare tuples of different sizes");
-#    endif
   return __tuple_equal<sizeof...(_Tp)>()(__x, __y);
 }
 
diff --git a/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp b/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
index 54936ea535c2b..851f6fcd1fbac 100644
--- a/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
+++ b/libcxx/test/std/utilities/tuple/tuple.tuple/tuple.rel/size_incompatible_comparison.verify.cpp
@@ -21,15 +21,9 @@
 
 #include <tuple>
 
-#include "test_macros.h"
-
 void f(std::tuple<int> t1, std::tuple<int, long> t2) {
   // We test only the core comparison operators and trust that the others
   // fall back on the same implementations prior to C++20.
-#if TEST_STD_VER >= 26
-  static_cast<void>(t1 == t2);
-#else
   static_cast<void>(t1 == t2); // expected-error@*:* {{}}
-#endif
   static_cast<void>(t1 < t2); // expected-error@*:* {{}}
 }
diff --git a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
index da78503abee48..e555978dacf23 100644
--- a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
+++ b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
@@ -25,27 +25,7 @@
 
 #if TEST_STD_VER >= 26
 
-// template <typename T>
-// class EqualityComparable {
-// public:
-//   constexpr EqualityComparable(T value) : value_{value} {};
-
-//   friend constexpr bool operator==(const EqualityComparable&, const EqualityComparable&) noexcept = default;
-
-// private:
-//   T value_;
-// };
-
-// static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, std::pair<int,int>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>, std::pair<int,int>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, EqualityComparable<std::pair<int,int>>>);
-// // static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>, EqualityComparable<std::pair<int,int>>>);
-// static_assert(std::equality_comparable<EqualityComparable<std::pair<int,int>>, std::pair<int,int>, std::pair<int,int>, EqualityComparable<std::pair<int,int>>>);
-// static_assert(EqualityComparable<std::pair<int,int>>{std::pair{94, 82}} == EqualityComparable<std::pair<int,int>>{std::pair{94, 82}});
-// static_assert(EqualityComparable<std::pair<int,int>>{std::pair{94, 82}} != EqualityComparable<std::pair<int,int>>{std::pair{82, 82}});
+// Test SFINAE.
 
 struct EqualityComparable {
   constexpr EqualityComparable(int value) : value_{value} {};
@@ -60,43 +40,15 @@ static_assert(EqualityComparable{94} == EqualityComparable{94});
 static_assert(EqualityComparable{94} != EqualityComparable{82});
 
 static_assert(std::equality_comparable<std::pair<EqualityComparable, EqualityComparable>>);
-static_assert(std::pair{EqualityComparable{94}, EqualityComparable{94}} ==
-              std::pair{EqualityComparable{94}, EqualityComparable{94}});
-static_assert(std::pair{EqualityComparable{82}, EqualityComparable{94}} !=
-              std::pair{EqualityComparable{94}, EqualityComparable{94}});
-static_assert(std::pair{EqualityComparable{94}, EqualityComparable{82}} !=
-              std::pair{EqualityComparable{94}, EqualityComparable{94}});
 
 struct NonComparable {};
 
-static_assert(!std::three_way_comparable<std::pair<NonComparable, NonComparable>>);
-static_assert(!std::three_way_comparable<std::pair<EqualityComparable, NonComparable>>);
-static_assert(!std::three_way_comparable<std::pair<NonComparable, EqualityComparable>>);
+static_assert(!std::equality_comparable<NonComparable>);
 
 static_assert(!std::equality_comparable<std::pair<EqualityComparable, NonComparable>>);
 static_assert(!std::equality_comparable<std::pair<NonComparable, EqualityComparable>>);
 
 
-template <typename T, typename U>
-concept HasCompare = requires(T t, U u) {
-  { t == u } -> std::same_as<bool>;
-  { t != u } -> std::same_as<bool>;
-  { t < u } -> std::same_as<bool>;
-  { t > u } -> std::same_as<bool>;
-  { t <= u } -> std::same_as<bool>;
-  { t >= u } -> std::same_as<bool>;
-};
-
-template <typename T, typename U>
-concept HasCompare = requires(std::pair p1, std::pair p2) {
-  { t == u } -> std::same_as<bool>;
-  { t != u } -> std::same_as<bool>;
-  { t < u } -> std::same_as<bool>;
-  { t > u } -> std::same_as<bool>;
-  { t <= u } -> std::same_as<bool>;
-  { t >= u } -> std::same_as<bool>;
-};
-
 #endif // TEST_STD_VER >= 26
 
 int main(int, char**)

>From 92544cb796bda03f59eda61060a42baa006cb407 Mon Sep 17 00:00:00 2001
From: Hristo Hristov <hghristov.rmm at gmail.com>
Date: Tue, 22 Apr 2025 12:24:07 +0300
Subject: [PATCH 3/6] Cleanup test

---
 .../std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp  | 2 --
 1 file changed, 2 deletions(-)

diff --git a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
index e555978dacf23..597400b84fd9e 100644
--- a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
+++ b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
@@ -36,8 +36,6 @@ struct EqualityComparable {
 };
 
 static_assert(std::equality_comparable<EqualityComparable>);
-static_assert(EqualityComparable{94} == EqualityComparable{94});
-static_assert(EqualityComparable{94} != EqualityComparable{82});
 
 static_assert(std::equality_comparable<std::pair<EqualityComparable, EqualityComparable>>);
 

>From 672c7c31ea2a861f4f86165bc2f27b616c1f754f Mon Sep 17 00:00:00 2001
From: Hristo Hristov <hghristov.rmm at gmail.com>
Date: Tue, 22 Apr 2025 12:29:21 +0300
Subject: [PATCH 4/6] Fix CI

---
 .../std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp   | 1 -
 1 file changed, 1 deletion(-)

diff --git a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
index 597400b84fd9e..c472906c5ed7f 100644
--- a/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
+++ b/libcxx/test/std/utilities/utility/pairs/pairs.spec/comparison.pass.cpp
@@ -46,7 +46,6 @@ static_assert(!std::equality_comparable<NonComparable>);
 static_assert(!std::equality_comparable<std::pair<EqualityComparable, NonComparable>>);
 static_assert(!std::equality_comparable<std::pair<NonComparable, EqualityComparable>>);
 
-
 #endif // TEST_STD_VER >= 26
 
 int main(int, char**)

>From 3079b7050c1cd1c7017fb02d62ad081007091fde Mon Sep 17 00:00:00 2001
From: Hristo Hristov <hghristov.rmm at gmail.com>
Date: Tue, 22 Apr 2025 12:33:57 +0300
Subject: [PATCH 5/6] Fix docs gen

---
 libcxx/docs/Status/Cxx2cPapers.csv | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/libcxx/docs/Status/Cxx2cPapers.csv b/libcxx/docs/Status/Cxx2cPapers.csv
index f29de08ba7b5f..0ed0e9f3ccb7c 100644
--- a/libcxx/docs/Status/Cxx2cPapers.csv
+++ b/libcxx/docs/Status/Cxx2cPapers.csv
@@ -59,7 +59,7 @@
 "`P2248R8 <https://wg21.link/P2248R8>`__","Enabling list-initialization for algorithms","2024-03 (Tokyo)","","",""
 "`P2810R4 <https://wg21.link/P2810R4>`__","``is_debugger_present`` ``is_replaceable``","2024-03 (Tokyo)","","",""
 "`P1068R11 <https://wg21.link/P1068R11>`__","Vector API for random number generation","2024-03 (Tokyo)","","",""
-"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","21","Implemented changes to ``reference_wrapper``, ``pair`"
+"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","21","Implemented changes to ``reference_wrapper``, ``pair``"
 "`P2642R6 <https://wg21.link/P2642R6>`__","Padded ``mdspan`` layouts","2024-03 (Tokyo)","","",""
 "`P3029R1 <https://wg21.link/P3029R1>`__","Better ``mdspan``'s CTAD","2024-03 (Tokyo)","|Complete|","19",""
 "","","","","",""

>From 40b04ce69f15015bc0d60d284e772f7b1ebacac2 Mon Sep 17 00:00:00 2001
From: Hristo Hristov <zingam at outlook.com>
Date: Wed, 23 Apr 2025 13:24:23 +0300
Subject: [PATCH 6/6] Update libcxx/docs/Status/Cxx2cPapers.csv

Co-authored-by: Nikolas Klauser <nikolasklauser at berlin.de>
---
 libcxx/docs/Status/Cxx2cPapers.csv | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/libcxx/docs/Status/Cxx2cPapers.csv b/libcxx/docs/Status/Cxx2cPapers.csv
index 0ed0e9f3ccb7c..eed71d36c67af 100644
--- a/libcxx/docs/Status/Cxx2cPapers.csv
+++ b/libcxx/docs/Status/Cxx2cPapers.csv
@@ -59,7 +59,7 @@
 "`P2248R8 <https://wg21.link/P2248R8>`__","Enabling list-initialization for algorithms","2024-03 (Tokyo)","","",""
 "`P2810R4 <https://wg21.link/P2810R4>`__","``is_debugger_present`` ``is_replaceable``","2024-03 (Tokyo)","","",""
 "`P1068R11 <https://wg21.link/P1068R11>`__","Vector API for random number generation","2024-03 (Tokyo)","","",""
-"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","21","Implemented changes to ``reference_wrapper``, ``pair``"
+"`P2944R3 <https://wg21.link/P2944R3>`__","Comparisons for ``reference_wrapper``","2024-03 (Tokyo)","|Partial|","21","Implemented changes to ``reference_wrapper`` and ``pair``"
 "`P2642R6 <https://wg21.link/P2642R6>`__","Padded ``mdspan`` layouts","2024-03 (Tokyo)","","",""
 "`P3029R1 <https://wg21.link/P3029R1>`__","Better ``mdspan``'s CTAD","2024-03 (Tokyo)","|Complete|","19",""
 "","","","","",""



More information about the libcxx-commits mailing list