|
24 | 24 |
|
25 | 25 | #include <sot/core/unary-op.hh>
|
26 | 26 | #include <sot/core/binary-op.hh>
|
| 27 | +#include <sot/core/variadic-op.hh> |
27 | 28 |
|
28 | 29 | #include <sot/core/matrix-geometry.hh>
|
29 | 30 |
|
@@ -745,58 +746,6 @@ namespace dynamicgraph {
|
745 | 746 | };
|
746 | 747 | REGISTER_BINARY_OP(VectorStack,Stack_of_vector);
|
747 | 748 |
|
748 |
| - /* --- STACK ------------------------------------------------------------ */ |
749 |
| - struct VectorMix |
750 |
| - : public BinaryOpHeader<dynamicgraph::Vector,dynamicgraph::Vector,dynamicgraph::Vector> |
751 |
| - { |
752 |
| - public: |
753 |
| - std::vector<bool> useV1; |
754 |
| - std::vector<int> idx1, idx2; |
755 |
| - void operator()( const dynamicgraph::Vector& v1,const dynamicgraph::Vector& v2,dynamicgraph::Vector& res ) const |
756 |
| - { |
757 |
| - res.resize(useV1.size()); |
758 |
| - std::size_t k1=0, k2=0; |
759 |
| - for (std::size_t i = 0; i < useV1.size(); ++i) |
760 |
| - { |
761 |
| - if (useV1[i]) { |
762 |
| - assert (k1 < idx1.size()); |
763 |
| - res[i] = v1[idx1[k1]]; |
764 |
| - ++k1; |
765 |
| - } else { |
766 |
| - assert (k2 < idx2.size()); |
767 |
| - res[i] = v2[idx2[k2]]; |
768 |
| - ++k2; |
769 |
| - } |
770 |
| - } |
771 |
| - assert (k1 == idx1.size()); |
772 |
| - assert (k2 == idx2.size()); |
773 |
| - } |
774 |
| - |
775 |
| - void addSelec1( const int & i) { useV1.push_back(true ); idx1.push_back(i); } |
776 |
| - void addSelec2( const int & i) { useV1.push_back(false); idx2.push_back(i); } |
777 |
| - |
778 |
| - void addSpecificCommands(Entity& ent, |
779 |
| - Entity::CommandMap_t& commandMap ) |
780 |
| - { |
781 |
| - using namespace dynamicgraph::command; |
782 |
| - |
783 |
| - boost::function< void( const int& ) > selec1 |
784 |
| - = boost::bind( &VectorMix::addSelec1,this,_1 ); |
785 |
| - boost::function< void( const int& ) > selec2 |
786 |
| - = boost::bind( &VectorMix::addSelec2,this,_1 ); |
787 |
| - |
788 |
| - ADD_COMMAND( "addSelec1", |
789 |
| - makeCommandVoid1(ent, selec1, |
790 |
| - docCommandVoid1("append value from vector 1.", |
791 |
| - "int (index in vector 1)"))); |
792 |
| - ADD_COMMAND( "addSelec2", |
793 |
| - makeCommandVoid1(ent, selec2, |
794 |
| - docCommandVoid1("append value from vector 2.", |
795 |
| - "int (index in vector 2)"))); |
796 |
| - } |
797 |
| - }; |
798 |
| - REGISTER_BINARY_OP(VectorMix,Mix_of_vector); |
799 |
| - |
800 | 749 | /* ---------------------------------------------------------------------- */
|
801 | 750 |
|
802 | 751 | struct Composer
|
@@ -968,6 +917,99 @@ namespace dynamicgraph {
|
968 | 917 | }
|
969 | 918 | }
|
970 | 919 |
|
| 920 | +#define REGISTER_VARIADIC_OP( OpType,name ) \ |
| 921 | + template<> \ |
| 922 | + const std::string VariadicOp< OpType >::CLASS_NAME = std::string(#name); \ |
| 923 | + Entity *regFunction##_##name( const std::string& objname ) \ |
| 924 | + { \ |
| 925 | + return new VariadicOp< OpType >( objname ); \ |
| 926 | + } \ |
| 927 | + EntityRegisterer regObj##_##name( std::string(#name),®Function##_##name) |
| 928 | + |
| 929 | +namespace dynamicgraph { |
| 930 | + namespace sot { |
| 931 | + template< typename Tin, typename Tout, typename Time > |
| 932 | + std::string VariadicAbstract<Tin,Tout,Time>::getTypeInName (void) { return TypeNameHelper<Tin>::typeName; } |
| 933 | + template< typename Tin, typename Tout, typename Time > |
| 934 | + std::string VariadicAbstract<Tin,Tout,Time>::getTypeOutName(void) { return TypeNameHelper<Tout>::typeName; } |
| 935 | + |
| 936 | + template< typename TypeIn, typename TypeOut > |
| 937 | + struct VariadicOpHeader |
| 938 | + { |
| 939 | + typedef TypeIn Tin ; |
| 940 | + typedef TypeOut Tout; |
| 941 | + static const std::string & nameTypeIn (void) { return TypeNameHelper<Tin >::typeName; } |
| 942 | + static const std::string & nameTypeOut(void) { return TypeNameHelper<Tout>::typeName; } |
| 943 | + template <typename Op> |
| 944 | + void initialize(VariadicOp<Op>*, Entity::CommandMap_t& ) {} |
| 945 | + virtual std::string getDocString () const |
| 946 | + { |
| 947 | + return std::string ( |
| 948 | + "Undocumented variadic operator\n" |
| 949 | + " - input " + nameTypeIn () + |
| 950 | + "\n" |
| 951 | + " - output " + nameTypeOut () + |
| 952 | + "\n"); |
| 953 | + } |
| 954 | + }; |
| 955 | + |
| 956 | + /* --- VectorMix ------------------------------------------------------------ */ |
| 957 | + struct VectorMix |
| 958 | + : public VariadicOpHeader<Vector,Vector> |
| 959 | + { |
| 960 | + public: |
| 961 | + typedef VariadicOp<VectorMix> Base; |
| 962 | + struct segment_t { |
| 963 | + Vector::Index index, size, input; |
| 964 | + std::size_t sigIdx; |
| 965 | + segment_t (Vector::Index i, Vector::Index s, std::size_t sig) : index (i), size(s), sigIdx (sig) {} |
| 966 | + }; |
| 967 | + typedef std::vector <segment_t> segments_t; |
| 968 | + Base* entity; |
| 969 | + segments_t idxs; |
| 970 | + void operator()( const std::vector<const Vector*>& vs, Vector& res ) const |
| 971 | + { |
| 972 | + res = *vs[0]; |
| 973 | + for (std::size_t i = 0; i < idxs.size(); ++i) |
| 974 | + { |
| 975 | + const segment_t& s = idxs[i]; |
| 976 | + if (s.sigIdx >= vs.size()) |
| 977 | + throw std::invalid_argument ("Index out of range in VectorMix"); |
| 978 | + res.segment (s.index, s.size) = *vs[s.sigIdx]; |
| 979 | + } |
| 980 | + } |
| 981 | + |
| 982 | + void addSelec( const int & sigIdx, const int & i, const int& s) { idxs.push_back(segment_t(i,s,sigIdx)); } |
| 983 | + |
| 984 | + void initialize(Base* ent, |
| 985 | + Entity::CommandMap_t& commandMap ) |
| 986 | + { |
| 987 | + using namespace dynamicgraph::command; |
| 988 | + entity = ent; |
| 989 | + |
| 990 | + ent->addSignal ("default"); |
| 991 | + |
| 992 | + boost::function< void( const int&, const int&, const int& ) > selec |
| 993 | + = boost::bind( &VectorMix::addSelec,this,_1,_2,_3 ); |
| 994 | + |
| 995 | + ADD_COMMAND( "setSignalNumber", makeCommandVoid1(*(typename Base::Base*)ent, &Base::setSignalNumber, |
| 996 | + docCommandVoid1("set the number of input vector.", "int (size)"))); |
| 997 | + |
| 998 | + commandMap.insert(std::make_pair( "getSignalNumber", |
| 999 | + new Getter<Base, int> (*ent, &Base::getSignalNumber, |
| 1000 | + "Get the number of input vector."))); |
| 1001 | + |
| 1002 | + commandMap.insert(std::make_pair("addSelec", |
| 1003 | + makeCommandVoid3<Base,int,int,int>(*ent, selec, |
| 1004 | + docCommandVoid3("add selection from a vector.", |
| 1005 | + "int (signal index >= 1)", "int (index)","int (size)")))); |
| 1006 | + } |
| 1007 | + }; |
| 1008 | + REGISTER_VARIADIC_OP(VectorMix,Mix_of_vector); |
| 1009 | + } |
| 1010 | +} |
| 1011 | + |
| 1012 | + |
971 | 1013 | /* --- TODO ------------------------------------------------------------------*/
|
972 | 1014 | // The following commented lines are sot-v1 entities that are still waiting
|
973 | 1015 | // for conversion. Help yourself!
|
|
0 commit comments