[multiple changes]
authorPaolo Carlini <paolo@gcc.gnu.org>
Wed, 30 Jun 2004 09:20:18 +0000 (09:20 +0000)
committerPaolo Carlini <paolo@gcc.gnu.org>
Wed, 30 Jun 2004 09:20:18 +0000 (09:20 +0000)
2004-06-30  Gabriel Dos Reis  <gdr@integrable-solutions.net>
            Paolo Carlini  <pcarlini@suse.de>

* include/bits/cpp_type_traits.h: Add __is_pointer and
__is_trivially_copyable.
* include/bits/stl_algobase.h (fill, fill_n): Slightly
tweak to use the latter.
(__copy_backward_dispatch): Remove.
(__copy_backward_aux): Rewrite to use __is_pointer and
__is_trivially_copyable and __copy_backward::copy_b.
(__copy_backward): Rewrite as a class template and two
specializations.

2004-06-30  Paolo Carlini  <pcarlini@suse.de>

* testsuite/25_algorithms/copy.cc: Move to...
* testsuite/25_algorithms/copy/1.cc: ... here, extend.
* testsuite/25_algorithms/copy/2.cc: New.
* testsuite/25_algorithms/copy/3.cc: New.
* testsuite/25_algorithms/copy/4.cc: New.

From-SVN: r83897

libstdc++-v3/ChangeLog
libstdc++-v3/include/bits/cpp_type_traits.h
libstdc++-v3/include/bits/stl_algobase.h
libstdc++-v3/testsuite/25_algorithms/copy.cc [deleted file]
libstdc++-v3/testsuite/25_algorithms/copy/1.cc [new file with mode: 0644]
libstdc++-v3/testsuite/25_algorithms/copy/2.cc [new file with mode: 0644]
libstdc++-v3/testsuite/25_algorithms/copy/3.cc [new file with mode: 0644]
libstdc++-v3/testsuite/25_algorithms/copy/4.cc [new file with mode: 0644]

index e433113f1f2b9641251c8cd38e404d8c46afd020..92158acffc04f611aabab953e7f4f240c0dd537d 100644 (file)
@@ -1,3 +1,24 @@
+2004-06-30  Gabriel Dos Reis  <gdr@integrable-solutions.net>
+            Paolo Carlini  <pcarlini@suse.de>
+
+       * include/bits/cpp_type_traits.h: Add __is_pointer and
+       __is_trivially_copyable.
+       * include/bits/stl_algobase.h (fill, fill_n): Slightly
+       tweak to use the latter.
+       (__copy_backward_dispatch): Remove.
+       (__copy_backward_aux): Rewrite to use __is_pointer and
+       __is_trivially_copyable and __copy_backward::copy_b.
+       (__copy_backward): Rewrite as a class template and two
+       specializations.
+
+2004-06-30  Paolo Carlini  <pcarlini@suse.de>
+
+       * testsuite/25_algorithms/copy.cc: Move to...
+       * testsuite/25_algorithms/copy/1.cc: ... here, extend.
+       * testsuite/25_algorithms/copy/2.cc: New.
+       * testsuite/25_algorithms/copy/3.cc: New.
+       * testsuite/25_algorithms/copy/4.cc: New.
+
 2004-06-29  Paul Brook  <paul@codesourcery.com>
 
        * libsupc++/vec.cc (__cxa_vec_new2, __cxa_vec_new3): Store the
index d4e4ea0410a50945994778f2d96831f1081b36a1..bf9254fd20423d09d41031f7493d1e37abd83080 100644 (file)
@@ -303,6 +303,27 @@ namespace std
        };
     };
 
+  //
+  // Pointer types
+  //
+  template<typename _Tp>
+    struct __is_pointer
+    {
+      enum
+       {
+         _M_type = 0
+       };
+    };
+
+  template<typename _Tp>
+    struct __is_pointer<_Tp*>
+    {
+      enum
+       {
+         _M_type = 1
+       };
+    };
+
   //
   // An arithmetic type is an integer type or a floating point type
   //
@@ -327,6 +348,18 @@ namespace std
        };
     };
 
+  //
+  // A trivially copyable type is an arithmetic type or a pointer type
+  // 
+  template<typename _Tp>
+    struct __is_trivially_copyable
+    {
+      enum
+       {
+         _M_type = __is_arithmetic<_Tp>::_M_type || __is_pointer<_Tp>::_M_type
+       };
+    };
+
   //
   // For the immediate use, the following is a good approximation
   //
index 0db0ef7daac92a14473eed807d0d1b00cc7fe366..1b7c4b49ad5d96d09258baed7fe93bf63b4dd432 100644 (file)
@@ -70,6 +70,7 @@
 #include <iosfwd>
 #include <bits/stl_pair.h>
 #include <bits/type_traits.h>
+#include <bits/cpp_type_traits.h>
 #include <bits/stl_iterator_base_types.h>
 #include <bits/stl_iterator_base_funcs.h>
 #include <bits/stl_iterator.h>
@@ -357,79 +358,59 @@ namespace std
        typedef typename _Is_normal_iterator<_InputIterator>::_Normal __Normal;
        return std::__copy_ni1(__first, __last, __result, __Normal());
     }
-
-  template<typename _BidirectionalIterator1, typename _BidirectionalIterator2>
-    inline _BidirectionalIterator2
-    __copy_backward(_BidirectionalIterator1 __first,
-                   _BidirectionalIterator1 __last,
-                   _BidirectionalIterator2 __result,
-                   bidirectional_iterator_tag)
-    {
-      while (__first != __last)
-        *--__result = *--__last;
-      return __result;
-    }
-
-  template<typename _RandomAccessIterator, typename _BidirectionalIterator>
-    inline _BidirectionalIterator
-    __copy_backward(_RandomAccessIterator __first, _RandomAccessIterator __last,
-                   _BidirectionalIterator __result, random_access_iterator_tag)
-    {
-      typename iterator_traits<_RandomAccessIterator>::difference_type __n;
-      for (__n = __last - __first; __n > 0; --__n)
-        *--__result = *--__last;
-      return __result;
-    }
-
-
-  // This dispatch class is a workaround for compilers that do not
-  // have partial ordering of function templates.  All we're doing is
-  // creating a specialization so that we can turn a call to copy_backward
-  // into a memmove whenever possible.
-  template<typename _BidirectionalIterator1, typename _BidirectionalIterator2,
-           typename _BoolType>
-    struct __copy_backward_dispatch
-    {
-      static _BidirectionalIterator2
-      copy(_BidirectionalIterator1 __first, _BidirectionalIterator1 __last,
-          _BidirectionalIterator2 __result)
-      { return std::__copy_backward(__first, __last, __result,
-                                   std::__iterator_category(__first)); }
+  
+  template<bool, typename>
+    struct __copy_backward
+    {
+      template<typename _BI1, typename _BI2>
+        static _BI2
+        copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
+        { 
+         while (__first != __last)
+           *--__result = *--__last;
+         return __result;
+       }
     };
 
-  template<typename _Tp>
-    struct __copy_backward_dispatch<_Tp*, _Tp*, __true_type>
-    {
-      static _Tp*
-      copy(const _Tp* __first, const _Tp* __last, _Tp* __result)
-      {
-       const ptrdiff_t _Num = __last - __first;
-       std::memmove(__result - _Num, __first, sizeof(_Tp) * _Num);
-       return __result - _Num;
-      }
+  template<bool _BoolType>
+    struct __copy_backward<_BoolType, random_access_iterator_tag>
+    {
+      template<typename _BI1, typename _BI2>
+        static _BI2
+        copy_b(_BI1 __first, _BI1 __last, _BI2 __result)
+        { 
+         typename iterator_traits<_BI1>::difference_type __n;
+         for (__n = __last - __first; __n > 0; --__n)
+           *--__result = *--__last;
+         return __result;
+       }
     };
 
-  template<typename _Tp>
-    struct __copy_backward_dispatch<const _Tp*, _Tp*, __true_type>
-    {
-      static _Tp*
-      copy(const _Tp* __first, const _Tp* __last, _Tp* __result)
-      {
-       return  std::__copy_backward_dispatch<_Tp*, _Tp*, __true_type>
-         ::copy(__first, __last, __result);
-      }
+  template<>
+    struct __copy_backward<true, random_access_iterator_tag>
+    {
+      template<typename _Tp>
+        static _Tp*
+        copy_b(const _Tp* __first, const _Tp* __last, _Tp* __result)
+        { 
+         const ptrdiff_t _Num = __last - __first;
+         std::memmove(__result - _Num, __first, sizeof(_Tp) * _Num);
+         return __result - _Num;
+       }
     };
 
   template<typename _BI1, typename _BI2>
     inline _BI2
     __copy_backward_aux(_BI1 __first, _BI1 __last, _BI2 __result)
     {
-      typedef typename __type_traits<typename iterator_traits<_BI2>::value_type>
-                           ::has_trivial_assignment_operator _Trivial;
-      return
-       std::__copy_backward_dispatch<_BI1, _BI2, _Trivial>::copy(__first,
-                                                                 __last,
-                                                                 __result);
+      typedef typename iterator_traits<_BI2>::value_type _ValueType;
+      typedef typename iterator_traits<_BI1>::iterator_category _Category;
+      const bool __simple = (__is_trivially_copyable<_ValueType>::_M_type
+                            && __is_pointer<_BI1>::_M_type
+                            && __is_pointer<_BI2>::_M_type);
+
+      return __copy_backward<__simple, _Category>::copy_b(__first, __last,
+                                                         __result);
     }
 
   template <typename _BI1, typename _BI2>
@@ -499,7 +480,7 @@ namespace std
                                                        __result, __Normal());
     }
 
-  template<typename>
+  template<bool>
     struct __fill
     {
       template<typename _ForwardIterator, typename _Tp>
@@ -513,7 +494,7 @@ namespace std
     };
 
   template<>
-    struct __fill<__true_type>
+    struct __fill<true>
     {
       template<typename _ForwardIterator, typename _Tp>
         static void
@@ -546,9 +527,8 @@ namespace std
                                  _ForwardIterator>)
       __glibcxx_requires_valid_range(__first, __last);
 
-      typedef typename __type_traits<_Tp>::has_trivial_copy_constructor
-       _Trivial;
-      std::__fill<_Trivial>::fill(__first, __last, __value);
+      const bool __trivial = __is_trivially_copyable<_Tp>::_M_type;
+      std::__fill<__trivial>::fill(__first, __last, __value);
     }
 
   // Specialization: for one-byte types we can use memset.
@@ -576,7 +556,7 @@ namespace std
     std::memset(__first, static_cast<unsigned char>(__tmp), __last - __first);
   }
 
-  template<typename>
+  template<bool>
     struct __fill_n
     {
       template<typename _OutputIterator, typename _Size, typename _Tp>
@@ -590,7 +570,7 @@ namespace std
     };
 
   template<>
-    struct __fill_n<__true_type>
+    struct __fill_n<true>
     {
       template<typename _OutputIterator, typename _Size, typename _Tp>
         static _OutputIterator
@@ -621,9 +601,8 @@ namespace std
       // concept requirements
       __glibcxx_function_requires(_OutputIteratorConcept<_OutputIterator, _Tp>)
 
-      typedef typename __type_traits<_Tp>::has_trivial_copy_constructor
-       _Trivial;
-      return std::__fill_n<_Trivial>::fill_n(__first, __n, __value);
+      const bool __trivial = __is_trivially_copyable<_Tp>::_M_type;
+      return std::__fill_n<__trivial>::fill_n(__first, __n, __value);
     }
 
   template<typename _Size>
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy.cc b/libstdc++-v3/testsuite/25_algorithms/copy.cc
deleted file mode 100644 (file)
index 6e69911..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-// Copyright (C) 2001 Free Software Foundation, Inc.
-//
-// This file is part of the GNU ISO C++ Library.  This library is free
-// software; you can redistribute it and/or modify it under the
-// terms of the GNU General Public License as published by the
-// Free Software Foundation; either version 2, or (at your option)
-// any later version.
-
-// This library is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without Pred the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-// GNU General Public License for more details.
-
-// You should have received a copy of the GNU General Public License along
-// with this library; see the file COPYING.  If not, write to the Free
-// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
-// USA.
-
-// 25.2.12 [lib.alg.partitions] Partitions.
-
-#include <algorithm>
-#include <testsuite_hooks.h>
-
-bool test __attribute__((unused)) = true;
-
-const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
-const int N = sizeof(A) / sizeof(int);
-
-// copy
-void
-test01()
-{
-    using std::copy;
-
-    int s1[N];
-    copy(A, A + N, s1);
-    VERIFY(std::equal(s1, s1 + N, A));
-}
-
-// copy_backward
-void
-test02()
-{
-    using std::copy_backward;
-
-    int s1[N];
-    copy_backward(A, A + N, s1 + N);
-    VERIFY(std::equal(s1, s1 + N, A));
-}
-
-int
-main()
-{
-  test01();
-  test02();
-
-  return 0;
-}
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy/1.cc b/libstdc++-v3/testsuite/25_algorithms/copy/1.cc
new file mode 100644 (file)
index 0000000..8574522
--- /dev/null
@@ -0,0 +1,56 @@
+// Copyright (C) 2001 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without Pred the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+// USA.
+
+// 25.2.1 [lib.alg.copy] Copy.
+
+#include <algorithm>
+#include <vector>
+#include <testsuite_hooks.h>
+
+void
+test01()
+{
+  using namespace std;
+  bool test __attribute__((unused)) = true;
+
+  const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
+  const int N = sizeof(A) / sizeof(int);
+  
+  int s1[N];
+  copy(A, A + N, s1);
+  VERIFY( equal(s1, s1 + N, A) );
+
+  vector<int> v1(N);
+  copy(A, A + N, v1.begin());
+  VERIFY( equal(v1.begin(), v1.end(), A) );
+
+  int s2[N];
+  copy_backward(A, A + N, s2 + N);
+  VERIFY( equal(s2, s2 + N, A) );
+
+  vector<int> v2(N);
+  copy_backward(A, A + N, v2.end());
+  VERIFY( equal(v2.begin(), v2.end(), A) );
+}
+
+int
+main()
+{
+  test01();
+  return 0;
+}
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy/2.cc b/libstdc++-v3/testsuite/25_algorithms/copy/2.cc
new file mode 100644 (file)
index 0000000..d7bd179
--- /dev/null
@@ -0,0 +1,57 @@
+// Copyright (C) 2004 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without Pred the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+// USA.
+
+// 25.2.1 [lib.alg.copy] Copy.
+
+#include <algorithm>
+#include <vector>
+#include <testsuite_hooks.h>
+
+void
+test01()
+{
+  using namespace std;
+  bool test __attribute__((unused)) = true;
+
+  const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
+  const int N = sizeof(A) / sizeof(int);
+  const vector<int> a(A, A + N);
+
+  int s1[N];
+  copy(a.begin(), a.end(), s1);
+  VERIFY( equal(s1, s1 + N, a.begin()) );
+
+  vector<int> v1(N);
+  copy(a.begin(), a.end(), v1.begin());
+  VERIFY( equal(v1.begin(), v1.end(), a.begin()) );
+
+  int s2[N];
+  copy_backward(a.begin(), a.end(), s2 + N);
+  VERIFY( equal(s2, s2 + N, a.begin()) );
+
+  vector<int> v2(N);
+  copy_backward(a.begin(), a.end(), v2.end());
+  VERIFY( equal(v2.begin(), v2.end(), a.begin()) );
+}
+
+int
+main()
+{
+  test01();
+  return 0;
+}
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy/3.cc b/libstdc++-v3/testsuite/25_algorithms/copy/3.cc
new file mode 100644 (file)
index 0000000..0453ce8
--- /dev/null
@@ -0,0 +1,58 @@
+// Copyright (C) 2004 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without Pred the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+// USA.
+
+// 25.2.1 [lib.alg.copy] Copy.
+
+#include <algorithm>
+#include <vector>
+#include <deque>
+#include <testsuite_hooks.h>
+
+void
+test01()
+{
+  using namespace std;
+  bool test __attribute__((unused)) = true;
+
+  const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
+  const int N = sizeof(A) / sizeof(int);
+  const deque<int> a(A, A + N);
+
+  int s1[N];
+  copy(a.begin(), a.end(), s1);
+  VERIFY( equal(s1, s1 + N, a.begin()) );
+
+  vector<int> v1(N);
+  copy(a.begin(), a.end(), v1.begin());
+  VERIFY( equal(v1.begin(), v1.end(), a.begin()) );
+
+  int s2[N];
+  copy_backward(a.begin(), a.end(), s2 + N);
+  VERIFY( equal(s2, s2 + N, a.begin()) );
+
+  vector<int> v2(N);
+  copy_backward(a.begin(), a.end(), v2.end());
+  VERIFY( equal(v2.begin(), v2.end(), a.begin()) );
+}
+
+int
+main()
+{
+  test01();
+  return 0;
+}
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy/4.cc b/libstdc++-v3/testsuite/25_algorithms/copy/4.cc
new file mode 100644 (file)
index 0000000..703adf8
--- /dev/null
@@ -0,0 +1,58 @@
+// Copyright (C) 2004 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without Pred the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+// USA.
+
+// 25.2.1 [lib.alg.copy] Copy.
+
+#include <algorithm>
+#include <vector>
+#include <list>
+#include <testsuite_hooks.h>
+
+void
+test01()
+{
+  using namespace std;
+  bool test __attribute__((unused)) = true;
+
+  const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
+  const int N = sizeof(A) / sizeof(int);
+  const list<int> a(A, A + N);
+  
+  int s1[N];
+  copy(a.begin(), a.end(), s1);
+  VERIFY( equal(s1, s1 + N, a.begin()) );
+
+  vector<int> v1(N);
+  copy(a.begin(), a.end(), v1.begin());
+  VERIFY( equal(v1.begin(), v1.end(), a.begin()) );
+
+  int s2[N];
+  copy_backward(a.begin(), a.end(), s2 + N);
+  VERIFY( equal(s2, s2 + N, a.begin()) );
+
+  vector<int> v2(N);
+  copy_backward(a.begin(), a.end(), v2.end());
+  VERIFY( equal(v2.begin(), v2.end(), a.begin()) );
+}
+
+int
+main()
+{
+  test01();
+  return 0;
+}