fork download
  1. #pragma once
  2. #include <type_traits>
  3. #include <typeinfo>
  4. #include <stdexcept>
  5. class any {
  6. public:
  7. any() : ptr(nullptr) {}
  8.  
  9. ~any() throw() { ptr.reset(); }
  10.  
  11. /// 복사 생성자
  12. any(const any& src) : ptr(src.clone()) {}
  13.  
  14. /// 이동 생성자
  15. any(any&& src) : ptr(src.clone()) {}
  16. template <class T> any(const T& src) : ptr(new holder<T>(src)) {}
  17. template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
  18.  
  19. template <class T> bool is() const {
  20. return dynamic_cast<holder<T>*>(ptr.get()) != NULL;
  21. }
  22.  
  23. template <class T> T& as() const{
  24.  
  25. auto Derived = dynamic_cast<holder<T>*>(ptr.get());
  26.  
  27. if(!Derived)
  28. throw bad_cast();
  29.  
  30. return Derived->value;
  31. }
  32.  
  33. template<class T> operator T()
  34. {
  35. return as<T>();
  36. }
  37. any& operator=(const any& src) {
  38. if(ptr != src.ptr){
  39. ptr.reset(src.clone());
  40. }
  41. return * this;
  42. }
  43. any& operator=(any&& src) {
  44. if(ptr.get() != src.ptr.get()){
  45. std::swap(ptr,src.ptr);
  46. }
  47. return *this;
  48. }
  49.  
  50. template <class T>
  51. any& operator=(const T& src) {
  52. ptr.reset(new holder<T>(src));
  53. return *this;
  54. }
  55.  
  56.  
  57. bool empty() const { return !ptr; }
  58.  
  59. const std::type_info& type() const {
  60. return ptr ? ptr->type() : typeid(void);
  61. }
  62.  
  63. template <class T> T& cast() const {
  64. return as<T>();
  65. }
  66. private:
  67. class base {
  68. public:
  69. virtual ~base() throw() {}
  70. virtual base* clone() const =0;
  71. virtual const std::type_info& type() const = 0;
  72. };
  73.  
  74. template <class T>
  75. class holder : public base {
  76. public:
  77. holder(const T& value_) : value(value_) {}
  78. virtual ~holder() throw() {}
  79. virtual base* clone() const { return new holder<T>(value); }
  80. virtual const std::type_info& type() const { return typeid(T); }
  81. T value;
  82. };
  83. base* clone() const
  84. {
  85. return ptr ? ptr->clone() : nullptr;
  86. }
  87.  
  88. std::unique_ptr<base> ptr;
  89. };
Compilation error #stdin compilation error #stdout 0s 0KB
stdin
Standard input is empty
compilation info
prog.cpp:1:9: warning: #pragma once in main file
 #pragma once
         ^
In file included from /usr/include/c++/4.9/type_traits:35:0,
                 from prog.cpp:2:
/usr/include/c++/4.9/bits/c++0x_warning.h:32:2: error: #error This file requires compiler and library support for the ISO C++ 2011 standard. This support is currently experimental, and must be enabled with the -std=c++11 or -std=gnu++11 compiler options.
 #error This file requires compiler and library support for the \
  ^
prog.cpp:15:9: error: expected ',' or '...' before '&&' token
  any(any&& src) : ptr(src.clone()) {}
         ^
prog.cpp:15:15: error: invalid constructor; you probably meant 'any (const any&)'
  any(any&& src) : ptr(src.clone()) {}
               ^
prog.cpp:17:26: error: expected ',' or '...' before '&&' token
  template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
                          ^
prog.cpp:43:20: error: expected ',' or '...' before '&&' token
  any& operator=(any&& src) {
                    ^
prog.cpp:88:7: error: 'unique_ptr' in namespace 'std' does not name a template type
  std::unique_ptr<base> ptr;
       ^
prog.cpp: In constructor 'any::any()':
prog.cpp:7:10: error: class 'any' does not have any field named 'ptr'
  any() : ptr(nullptr) {}
          ^
prog.cpp:7:14: error: 'nullptr' was not declared in this scope
  any() : ptr(nullptr) {}
              ^
prog.cpp: In destructor 'any::~any()':
prog.cpp:9:19: error: 'ptr' was not declared in this scope
  ~any() throw() { ptr.reset(); }
                   ^
prog.cpp: In copy constructor 'any::any(const any&)':
prog.cpp:12:24: error: class 'any' does not have any field named 'ptr'
  any(const any& src) : ptr(src.clone()) {}
                        ^
prog.cpp: In constructor 'any::any(const T&)':
prog.cpp:16:41: error: class 'any' does not have any field named 'ptr'
  template <class T> any(const T& src) : ptr(new holder<T>(src)) {}
                                         ^
prog.cpp: In constructor 'any::any(T)':
prog.cpp:17:36: error: class 'any' does not have any field named 'ptr'
  template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
                                    ^
prog.cpp:17:54: error: 'forward' is not a member of 'std'
  template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
                                                      ^
prog.cpp:17:68: error: expected primary-expression before '>' token
  template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
                                                                    ^
prog.cpp:17:70: error: 'src' was not declared in this scope
  template <class T> any(T&& src) : ptr(new holder<T>(std::forward<T>(src))) {}
                                                                      ^
prog.cpp: In member function 'bool any::is() const':
prog.cpp:20:35: error: 'ptr' was not declared in this scope
   return dynamic_cast<holder<T>*>(ptr.get()) != NULL;
                                   ^
prog.cpp: In member function 'T& any::as() const':
prog.cpp:25:8: error: 'Derived' does not name a type
   auto Derived = dynamic_cast<holder<T>*>(ptr.get());
        ^
prog.cpp:27:7: error: 'Derived' was not declared in this scope
   if(!Derived)
       ^
prog.cpp:28:19: error: there are no arguments to 'bad_cast' that depend on a template parameter, so a declaration of 'bad_cast' must be available [-fpermissive]
    throw bad_cast();
                   ^
prog.cpp:28:19: note: (if you use '-fpermissive', G++ will accept your code, but allowing the use of an undeclared name is deprecated)
prog.cpp:30:10: error: 'Derived' was not declared in this scope
   return Derived->value;
          ^
prog.cpp: In member function 'any& any::operator=(const any&)':
prog.cpp:38:6: error: 'ptr' was not declared in this scope
   if(ptr != src.ptr){
      ^
prog.cpp:38:17: error: 'const class any' has no member named 'ptr'
   if(ptr != src.ptr){
                 ^
prog.cpp: In member function 'any& any::operator=(any)':
prog.cpp:44:6: error: 'ptr' was not declared in this scope
   if(ptr.get() != src.ptr.get()){
      ^
prog.cpp:44:19: error: 'src' was not declared in this scope
   if(ptr.get() != src.ptr.get()){
                   ^
prog.cpp: In member function 'any& any::operator=(const T&)':
prog.cpp:52:3: error: 'ptr' was not declared in this scope
   ptr.reset(new holder<T>(src));
   ^
prog.cpp: In member function 'bool any::empty() const':
prog.cpp:57:31: error: 'ptr' was not declared in this scope
  bool empty() const { return !ptr; }
                               ^
prog.cpp: In member function 'const std::type_info& any::type() const':
prog.cpp:60:10: error: 'ptr' was not declared in this scope
   return ptr ? ptr->type() : typeid(void);
          ^
prog.cpp: In member function 'any::base* any::clone() const':
prog.cpp:85:10: error: 'ptr' was not declared in this scope
   return ptr ? ptr->clone() : nullptr;
          ^
prog.cpp:85:31: error: 'nullptr' was not declared in this scope
   return ptr ? ptr->clone() : nullptr;
                               ^
stdout
Standard output is empty