added new shared pointer with simpler interface; refs #7

master
Marc Wäckerlin 11 years ago
parent 1b2fa0d722
commit 80c2dc4d52
  1. 11
      configure.in
  2. 4
      doc/examples/makefile.am
  3. 30
      doc/examples/shared.cxx
  4. 2
      src/makefile.am
  5. 22
      src/mrw/deque.hxx
  6. 24
      src/mrw/list.hxx
  7. 30
      src/mrw/map.hxx
  8. 28
      src/mrw/multimap.hxx
  9. 24
      src/mrw/multiset.hxx
  10. 28
      src/mrw/set.hxx
  11. 88
      src/mrw/shared.hxx
  12. 6
      src/stacktrace.cxx

@ -1,4 +1,5 @@
# $Id$ # $Id$
set +x
m4_include(ax_cxx_compile_stdcxx_11.m4) m4_include(ax_cxx_compile_stdcxx_11.m4)
AC_ALIAS([AC_DEFINE_DIR], [AX_DEFINE_DIR]) AC_ALIAS([AC_DEFINE_DIR], [AX_DEFINE_DIR])
AC_DEFUN([AX_DEFINE_DIR], [ AC_DEFUN([AX_DEFINE_DIR], [
@ -23,7 +24,7 @@ DOC_DIR=doc
m4_define(x_packagename, mrw-c++) m4_define(x_packagename, mrw-c++)
m4_define(x_major, 4) m4_define(x_major, 4)
m4_define(x_minor, 0) m4_define(x_minor, 1)
PACKAGENAME=x_packagename PACKAGENAME=x_packagename
MAJOR=x_major MAJOR=x_major
MINOR=x_minor MINOR=x_minor
@ -33,9 +34,12 @@ if svn info . 2>&1 > /dev/null; then
LEAST=$(LANG= svn info $path | sed -n 's/Revision: //p') LEAST=$(LANG= svn info $path | sed -n 's/Revision: //p')
break; break;
else else
LEAST=[$(pwd | sed -n 's,^.*/'${PACKAGENAME}'-'${MAJOR}'\.'${MINOR}'\.\([0-9]*\).*$,\1,p')] MAJOR=[$(pwd | sed -n 's,^.*/'${PACKAGENAME}'-\([0-9]*\)\.\([0-9]*\)\.\([0-9]*\).*$,\1,p')]
MINOR=[$(pwd | sed -n 's,^.*/'${PACKAGENAME}'-\([0-9]*\)\.\([0-9]*\)\.\([0-9]*\).*$,\2,p')]
LEAST=[$(pwd | sed -n 's,^.*/'${PACKAGENAME}'-\([0-9]*\)\.\([0-9]*\)\.\([0-9]*\).*$,\3,p')]
if test -z "${LEAST}"; then if test -z "${LEAST}"; then
LEAST="ERROR CANNOT DETERMINE REVISION NUMBER from $(pwd)" AC_MSG_ERROR([CANNOT DETERMINE REVISION NUMBER from $(pwd)
Got: ${MAJOR}.${MINOR}.${LEAST}])
fi fi
fi fi
@ -49,6 +53,7 @@ while test $MINOR -gt 255; do
MAJOR=$((MAJOR+1)) MAJOR=$((MAJOR+1))
done done
AC_MSG_NOTICE([Version number of $PACKAGENAME is: ${MAJOR}.${MINOR}.${LEAST}])
AM_INIT_AUTOMAKE($PACKAGENAME, $MAJOR.$MINOR.$LEAST, [marc@waeckerlin.org]) AM_INIT_AUTOMAKE($PACKAGENAME, $MAJOR.$MINOR.$LEAST, [marc@waeckerlin.org])
# files to create # files to create

@ -4,7 +4,7 @@
## 45678901234567890123456789012345678901234567890123456789012345678901234567890 ## 45678901234567890123456789012345678901234567890123456789012345678901234567890
exampledir = ${docdir}/examples exampledir = ${docdir}/examples
example_PROGRAMS = smartpointer arguments example_PROGRAMS = smartpointer arguments shared
if HAVE_STACKTRACE if HAVE_STACKTRACE
example_PROGRAMS += exceptionhandling example_PROGRAMS += exceptionhandling
endif endif
@ -24,4 +24,6 @@ smartpointer_LDADD = ${top_builddir}/src/.libs/libmrw.la
arguments_SOURCES = arguments.cxx arguments_SOURCES = arguments.cxx
shared_SOURCES = shared.cxx
MAINTAINERCLEANFILES = makefile.in MAINTAINERCLEANFILES = makefile.in

@ -0,0 +1,30 @@
/*! @file
@id $Id$
*/
// 1 2 3 4 5 6 7 8
// 45678901234567890123456789012345678901234567890123456789012345678901234567890
#include <mrw/shared.hxx>
#include <iostream>
class Test {
public:
Test(int i): _int1(i), _int2(0) {}
Test(int i, int j): _int1(i), _int2(j) {}
int _int1;
int _int2;
};
int main(int, char**) {
mrw::Shared<Test> test1(15);
mrw::Shared<Test> test2(13, 14);
mrw::Shared<Test> test3(new Test(13));
mrw::Shared<Test> test4(test2);
std::cout<<"test1="<<test1->_int1<<", "<<test1->_int2<<std::endl
<<"test2="<<test2->_int1<<", "<<test2->_int2<<std::endl
<<"test3="<<test3->_int1<<", "<<test3->_int2<<std::endl
<<"test4="<<test4->_int1<<", "<<test4->_int2<<std::endl;
return 0;
}

@ -15,7 +15,7 @@ nobase_include_HEADERS = mrw/arg.hxx mrw/auto.hxx mrw/configfile.hxx \
mrw/stdext.hxx mrw/string.hxx \ mrw/stdext.hxx mrw/string.hxx \
mrw/tokenizer.hxx mrw/unistd.hxx \ mrw/tokenizer.hxx mrw/unistd.hxx \
mrw/vector.hxx mrw/args.hxx mrw/iomanip.hxx \ mrw/vector.hxx mrw/args.hxx mrw/iomanip.hxx \
mrw/checkcxx11.hxx mrw/checkcxx11.hxx mrw/shared.hxx
if HAVE_STACKTRACE if HAVE_STACKTRACE
AM_CPPFLAGS += -DHAVE_STACKTRACE AM_CPPFLAGS += -DHAVE_STACKTRACE

@ -50,12 +50,32 @@
@pre \#include <mrw/deque.hxx> @pre \#include <mrw/deque.hxx>
*/ */
template <typename T, typename A> template <typename T, typename A>
std::deque<T, A> operator<<(std::deque<T, A> l, const T& o) std::deque<T, A>& operator<<(std::deque<T, A>& l, const T& o)
throw(std::bad_exception) { throw(std::bad_exception) {
l.push_back(o); l.push_back(o);
return l; return l;
} }
/** @brief push a value to a constant deque
Makes a copy and returns the copy.
@code
std::deque<int>()<<1<<2<<3<<4<<5<<6<<7<<8;
@endcode
@param l a deque of values
@param o a value to be inserted into deque @c l
@pre \#include <mrw/deque.hxx>
*/
template <typename T, typename A>
std::deque<T, A> operator<<(const std::deque<T, A>& l, const T& o)
throw(std::bad_exception) {
std::deque<T, A> copy(l);
copy.push_back(o);
return copy;
}
/** @brief extract the first value of a deque /** @brief extract the first value of a deque
@code @code

@ -65,15 +65,35 @@
@param l a list of values @param l a list of values
@param o a value to be inserted into list @c l @param o a value to be inserted into list @c l
@pre \#include <mrw/list.hxx> @pre #include <mrw/list.hxx>
*/ */
template <typename T, typename A> template <typename T, typename A>
std::list<T, A> operator<<(std::list<T, A> l, const T& o) std::list<T, A>& operator<<(std::list<T, A>& l, const T& o)
throw(std::bad_exception) { throw(std::bad_exception) {
l.push_back(o); l.push_back(o);
return l; return l;
} }
/** @brief push a value to a constant list
Makes a copy and returns the copy.
@code
std::list<int>()<<1<<2<<3<<4<<5<<6<<7<<8;
@endcode
@param l a list of values
@param o a value to be inserted into list @c l
@pre #include <mrw/list.hxx>
*/
template <typename T, typename A>
std::list<T, A> operator<<(const std::list<T, A>& l, const T& o)
throw(std::bad_exception) {
std::list<T, A> copy(l);
copy.push_back(o);
return ;
}
/* @brief push a char* to a list of string /* @brief push a char* to a list of string
@code @code

@ -52,7 +52,7 @@
@pre \#include <mrw/map.hxx> @pre \#include <mrw/map.hxx>
*/ */
template <typename K, typename T, class C, typename A> template <typename K, typename T, class C, typename A>
std::map<K, T, C, A> operator<<(std::map<K, T, C, A> l, std::map<K, T, C, A>& operator<<(std::map<K, T, C, A>& l,
const std::pair<K, T>& o) const std::pair<K, T>& o)
throw(std::exception) { throw(std::exception) {
if (!l.insert(o).second) if (!l.insert(o).second)
@ -63,6 +63,34 @@ template <typename K, typename T, class C, typename A>
return l; return l;
} }
/** @brief insert a value in a map
Makes a copy and returns the copy.
@code
std::map<int, std::string>()
<<std::make_pair(1, std::string("one"))
<<std::make_pair(2, std::string("two"));
@endcode
@throw mrw::invalid_argument, if element is already in map
@param l a map of values
@param o a value to be inserted into map @c l
@pre \#include <mrw/map.hxx>
*/
template <typename K, typename T, class C, typename A>
std::map<K, T, C, A> operator<<(const std::map<K, T, C, A>& l,
const std::pair<K, T>& o)
throw(std::exception) {
std::map<K, T, C, A> copy(l);
if (!copy.insert(o).second)
throw mrw::invalid_argument(std::string(__FILE__ ":")+__LINE__+
": std::map<>&"
" operator<<(std::map<>&, const T&),"
"map element already exists");
return copy;
}
/** @brief extract the first value of a map /** @brief extract the first value of a map
@code @code

@ -52,13 +52,37 @@
@pre \#include <mrw/multimap.hxx> @pre \#include <mrw/multimap.hxx>
*/ */
template <typename K, typename T, class C, typename A> template <typename K, typename T, class C, typename A>
std::multimap<K, T, C, A> operator<<(std::multimap<K, T, C, A> l, std::multimap<K, T, C, A>& operator<<(std::multimap<K, T, C, A>& l,
const std::pair<K, T>& o) const std::pair<K, T>& o)
throw(std::bad_exception) { throw(std::bad_exception) {
l.insert(o); l.insert(o);
return l; return l;
} }
/** @brief insert a value in a multimap
Makes a copy and returns the copy.
@code
std::multimap<int, std::string>()
<<std::make_pair(1, std::string("one"))
<<std::make_pair(2, std::string("two"));
@endcode
@throw mrw::invalid_argument, if element is already in multimap
@param l a multimap of values
@param o a value to be inserted into multimap @c l
@pre \#include <mrw/multimap.hxx>
*/
template <typename K, typename T, class C, typename A>
std::multimap<K, T, C, A> operator<<(const std::multimap<K, T, C, A>& l,
const std::pair<K, T>& o)
throw(std::bad_exception) {
std::multimap<K, T, C, A> copy(l);
copy.insert(o);
return copy;
}
/** @brief extract the first value of a multimap /** @brief extract the first value of a multimap
@code @code

@ -50,12 +50,34 @@
@pre \#include <mrw/multiset.hxx> @pre \#include <mrw/multiset.hxx>
*/ */
template <typename T, class C, typename A> template <typename T, class C, typename A>
std::multiset<T, C, A> operator<<(std::multiset<T, C, A> l, const T& o) std::multiset<T, C, A>& operator<<(std::multiset<T, C, A>& l, const T& o)
throw(std::bad_exception) { throw(std::bad_exception) {
l.insert(o); l.insert(o);
return l; return l;
} }
/** @brief insert a value in a multiset
Makes a copy and returns the copy.
@code
std::multiset<int> test;
test<<1<<2<<3<<4<<5<<6<<7<<8;
@endcode
@param l a multiset of values
@param o a value to be inserted into multiset @c l
@pre \#include <mrw/multiset.hxx>
*/
template <typename T, class C, typename A>
std::multiset<T, C, A> operator<<(const std::multiset<T, C, A>& l,
const T& o)
throw(std::bad_exception) {
std::multiset<T, C, A> copy(l);
copy.insert(o);
return copy;
}
/** @brief extract the first value of a multiset /** @brief extract the first value of a multiset
@code @code

@ -48,10 +48,10 @@
@throw mrw::invalid_argument, if element is already in set @throw mrw::invalid_argument, if element is already in set
@param l a set of values @param l a set of values
@param o a value to be inserted into set @c l @param o a value to be inserted into set @c l
@pre \#include <mrw/set.hxx> @pre #include <mrw/set.hxx>
*/ */
template <typename T, class C, typename A> template <typename T, class C, typename A>
std::set<T, C, A> operator<<(std::set<T, C, A> l, const T& o) std::set<T, C, A>& operator<<(std::set<T, C, A>& l, const T& o)
throw(std::exception) { throw(std::exception) {
if (!l.insert(o).second) if (!l.insert(o).second)
throw mrw::invalid_argument(std::string(__FILE__ ":")+__LINE__+ throw mrw::invalid_argument(std::string(__FILE__ ":")+__LINE__+
@ -60,6 +60,30 @@ template <typename T, class C, typename A>
return l; return l;
} }
/** @brief insert a value in a set
Makes a copy and returns the copy.
@code
std::set<int>()<<1<<2<<3<<4<<5<<6<<7<<8;
@endcode
@throw mrw::invalid_argument, if element is already in set
@param l a set of values
@param o a value to be inserted into set @c l
@pre #include <mrw/set.hxx>
*/
template <typename T, class C, typename A>
std::set<T, C, A> operator<<(const std::set<T, C, A>& l, const T& o)
throw(std::exception) {
std::set<T, C, A> copy(l);
if (!copy.insert(o).second)
throw mrw::invalid_argument(std::string(__FILE__ ":")+__LINE__+
": std::set<>::operator<<, "
"set element already exists");
return copy;
}
/** @brief extract the first value of a set /** @brief extract the first value of a set
@code @code

@ -0,0 +1,88 @@
/*! @file
@id $Id$
*/
// 1 2 3 4 5 6 7 8
// 45678901234567890123456789012345678901234567890123456789012345678901234567890
#ifndef __SHARED_HXX__
#define __SHARED_HXX__
#include <mrw/checkcxx11.hxx>
#include <memory>
namespace mrw {
//! Shared pointer with better usage than std::shared_ptr
/*! You can assign a pointer or even construct like an auto variable. */
template <typename T> class Shared: public std::shared_ptr<T> {
public:
//! Default empty construction
Shared() {}
Shared(T* t): std::shared_ptr<T>(std::shared_ptr<T>(t)) {}
//! Construction from std::shared_ptr
Shared(std::shared_ptr<T> t): std::shared_ptr<T>(t) {}
//! Constructor creates child with one argument
template <typename T1>
Shared(T1 t1):
std::shared_ptr<T>(new T(t1)) {
}
//! Constructor creates child with two arguments
template <typename T1, typename T2>
Shared(T1 t1, T2 t2):
std::shared_ptr<T>(new T(t1, t2)) {
}
//! Constructor creates child with three arguments
template <typename T1, typename T2, typename T3>
Shared(T1 t1, T2 t2, T3 t3):
std::shared_ptr<T>(new T(t1, t2, t3)) {
}
//! Constructor creates child with four arguments
template <typename T1, typename T2, typename T3, typename T4>
Shared(T1 t1, T2 t2, T3 t3, T4 t4):
std::shared_ptr<T>(new T(t1, t2, t3, t4)) {
}
//! Constructor creates child with five arguments
template <typename T1, typename T2, typename T3, typename T4, typename T5>
Shared(T1 t1, T2 t2, T3 t3, T4 t4, T5 t5):
std::shared_ptr<T>(new T(t1, t2, t3, t4, t5)) {
}
//! Constructor creates child with six arguments
template <typename T1, typename T2, typename T3, typename T4, typename T5,
typename T6>
Shared(T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6):
std::shared_ptr<T>(new T(t1, t2, t3, t4, t5, t6)) {
}
//! Constructor creates child with seven arguments
template <typename T1, typename T2, typename T3, typename T4, typename T5,
typename T6, typename T7>
Shared(T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, T7 t7):
std::shared_ptr<T>(new T(t1, t2, t3, t4, t5, t6, t7)) {
}
//! Constructor creates child with eight arguments
template <typename T1, typename T2, typename T3, typename T4, typename T5,
typename T6, typename T7, typename T8>
Shared(T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, T7 t7, T8 t8):
std::shared_ptr<T>(new T(t1, t2, t3, t4, t5, t6, t7, t8)) {
}
//! Constructor creates child with nine arguments
template <typename T1, typename T2, typename T3, typename T4, typename T5,
typename T6, typename T7, typename T8, typename T9>
Shared(T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, T7 t7, T8 t8, T9 t9):
std::shared_ptr<T>(new T(t1, t2, t3, t4, t5, t6, t7, t8, t9)) {
}
//! Assign from shared pointer
Shared& operator=(std::shared_ptr<T> t) {
std::shared_ptr<T>::operator=(t);
return *this;
}
//! Assign from pointer
Shared& operator=(T* t) {
std::shared_ptr<T>::operator=(std::shared_ptr<T>(t));
return *this;
}
};
}
#endif

@ -9,6 +9,7 @@
@license LGPL, see file <a href="license.html">COPYING</a> @license LGPL, see file <a href="license.html">COPYING</a>
*/ */
#include <mrw/stacktrace.hxx> #include <mrw/stacktrace.hxx>
#include <mrw/exec.hxx> #include <mrw/exec.hxx>
#include <mrw/string.hxx> #include <mrw/string.hxx>
@ -323,7 +324,7 @@ mrw::StackTrace::BinFiles mrw::StackTrace::filename()
prpsinfo_t status; prpsinfo_t status;
if (fd==-1 || ioctl(fd, PIOCPSINFO, &status)==-1) return res; if (fd==-1 || ioctl(fd, PIOCPSINFO, &status)==-1) return res;
s = status.pr_psargs; s = status.pr_psargs;
return res<<BinFiles::value_type(s.substr(0, s.find(' ')), (void*)0); res<<BinFiles::value_type(s.substr(0, s.find(' ')), (void*)0);
} }
# elif defined(__linux__) # elif defined(__linux__)
{ {
@ -346,16 +347,15 @@ mrw::StackTrace::BinFiles mrw::StackTrace::filename()
res<<BinFiles::value_type(lib, addr); res<<BinFiles::value_type(lib, addr);
} }
} catch (...) {} // ignore non matching lines } catch (...) {} // ignore non matching lines
return res;
} }
# else # else
{ {
# warning "Don't know how to get executable file name in your system!" # warning "Don't know how to get executable file name in your system!"
# warning "Impossible to get function names in stack trace!" # warning "Impossible to get function names in stack trace!"
# warning "Give the path to the executable to StackTrace::createSymtable!" # warning "Give the path to the executable to StackTrace::createSymtable!"
return res; // empty
} }
# endif # endif
return res;
} }
//---------------------------------------------------------------------------- //----------------------------------------------------------------------------

Loading…
Cancel
Save