2015-12-17 81 views
1

我想寫一個函數,它需要一個複雜的價值向量和計算雙元素的角度。我的代碼如下:使用本徵元素的操作使用unaryExpr

#include <iostream> 
#include <functional> 
#include <Eigen/Core> 
#include <complex> 

class Arg { 
public: 
    double operator()(std::complex<double> a) const 
    { 
     return std::arg(a); 
    } 
}; 

template <typename DerivedA, typename DerivedB> 
void ArgumentComputer(const Eigen::MatrixBase<DerivedA> &mat, const Eigen::MatrixBase<DerivedB> &_arg) 
{ 

    Eigen::MatrixBase<DerivedB>& arg = const_cast<decltype(arg)>(_arg); 

    // 1st try: 
    //arg = mat.unaryExpr(std::ptr_fun(std::arg<double>)); 

    //error: no matching function for call to ‘ptr_fun(<unresolved overloaded function type>)’ 

    // 2nd try: 
    // arg = mat.unaryExpr(Arg{}); 

    // error: static assertion failed: YOU_MIXED_DIFFERENT_NUMERIC_TYPES__YOU_NEED_TO_USE_THE_CAST_METHOD_OF_MATRIXBASE_TO_CAST_NUMERIC_TYPES_EXPLICITLY 

    // 3rd try: 
    arg = mat.unaryExpr(Arg{}).template cast<double>(); 

    // error: invalid static_cast from type ‘const std::complex<double>’ to type ‘double’ 
    // return static_cast<NewType>(x); 


} 

int main() 
{ 

    Eigen::MatrixXcd myMat = Eigen::MatrixXcd::Random(3, 3); 
    Eigen::MatrixXd Arg_myMat(3, 3); 

    ArgumentComputer(myMat, Arg_myMat); 

    std::cout << myMat << std::endl; 
    std::cout << Arg_myMat << std::endl; 

    return 0; 
} 

我第一次嘗試使用ptr_fun,但我想有一個解決類型的問題。然後我試着寫一個類作爲函子的類。在這種情況下,我得到錯誤說我需要做鑄造。當我投射時,我得到了static_cast錯誤。所有這三種情況都在代碼中給出,並且編譯器消息也作爲註釋添加。我的錯誤是什麼,如何正確書寫?

回答

1

你的問題是你在不知不覺中試圖將一個複數轉換爲實數。您看到std::arg的返回類型爲double,並且假設這是您的所得,但由於mat類型(MatrixXcd),因此實際上它是std::complex<double>。你的代碼可能看起來像:

// 1st try: 
//arg = mat.unaryExpr(std::ptr_fun(std::arg<double>)).real(); // Should work but doesn't resolve the template for some reason 

// 2nd try: 
arg = mat.unaryExpr(Arg{}).real(); // works 

我不是100%確定爲什麼你的第一次嘗試不起作用。您也可以使用函數代替仿函數:

double myArg(std::complex<double> a) 
{ 
    return std::arg(a); 
} 
//... 
arg = mat.unaryExpr(std::ptr_fun(myArg)).real();