2017-02-26 4 views
0

問題の説明(s.time_since_epoch()()カウント。):私はCythonを使用して、PythonでC++オブジェクトにアクセスしたい を。
python2 setup.py build_ext -iを実行しているとき、私はCython.Compiler.Errors.CompileErrorCythonは `二重に` Cython.Compiler.Errors.CompileError`を返す `

あなたは以下を見て、私はCythonは私のコードをコンパイルするために取得するように変更すべきかを教えてもらえ取得しますか?

$ python2 setup.py build_ext -i 
Compiling ds5.pyx because it changed. 
[1/1] Cythonizing ds5.pyx 

Error compiling Cython file: 
------------------------------------------------------------ 
... 

    cdef cppclass os_time_service: 
     #double get_time() const override 
     double get_time() 
     #static_cast<double>(ts.time_since_epoch().count()) 
     double (s.time_since_epoch().count()) 
            ^
------------------------------------------------------------ 

ds5.pyx:15:37: Expected '.', found 'count' 
Traceback (most recent call last): 
    File "setup.py", line 5, in <module> 
    ext_modules = cythonize("ds5.pyx")) 
    File "/usr/local/lib/python2.7/dist-packages/Cython/Build/Dependencies.py", line 934, in cythonize 
    cythonize_one(*args) 
    File "/usr/local/lib/python2.7/dist-packages/Cython/Build/Dependencies.py", line 1056, in cythonize_one 
    raise CompileError(None, pyx_file) 
Cython.Compiler.Errors.CompileError: ds5.pyx 

hファイル内の関連する行は、次のとおりです:

$ view backend.h 
#ifndef LIBREALSENSE_BACKEND_H 
#define LIBREALSENSE_BACKEND_H 

#include "../include/librealsense/rs.h"  // Inherit all type definitions in the public API 

#include <memory>  // For shared_ptr 
#include <functional> // For function 
#include <thread>  // For this_thread::sleep_for 
#include <vector> 
#include <algorithm> 
#include <set> 
#include <list> 



const uint16_t VID_INTEL_CAMERA  = 0x8086; 

namespace rsimpl 
{ 
    namespace uvc 
    { 
     class time_service 
     { 
     public: 
      virtual double get_time() const = 0; 
      ~time_service() = default; 
     }; 

     class os_time_service: public time_service 
     { 
     public: 
      double get_time() const override 
      { 
       auto ts = std::chrono::time_point_cast<std::chrono::milliseconds>(std::chrono::system_clock::now()); 
       return static_cast<double>(ts.time_since_epoch().count()); 
      } 
     }; 
... 

そして、私のPYXファイルは次のとおりです。

$ cat ds5.pyx 
# distutils: language = c++ 
# distutils: sources = uvc-v4l2.cpp 

cdef extern from "backend.h" namespace "rsimpl::uvc": 
    #const uint16_t VID_INTEL_CAMERA  = 0x8086 
    const unsigned short VID_INTEL_CAMERA  = 0x8086 
    cdef cppclass time_service: 
     #virtual double get_time() const = 0 
     double get_time() 

    cdef cppclass os_time_service: 
     #double get_time() const override 
     double get_time() 
     #static_cast<double>(ts.time_since_epoch().count()) 
     double (s.time_since_epoch().count()) 

cdef class os_time_service_c: 

    cdef os_time_service *_os_time_service_ptr 

    def __cinit__(self): 
     self._os_time_service_ptr = new os_time_service() 
     if self._os_time_service_ptr == NULL: 
      raise MemoryError() 

    def __dealloc__(self): 
     if self._os_time_service_ptr != NULL: 
      del self._os_time_service_ptr 

    cpdef double get_time(self): 
     return self._os_time_service_ptr.ts.time_since_epoch().count() 
私はCythonでコンパイルしようとすると、私が取得

環境:

Ubuntu 16.04 
Python 2.7.12 
Cython 0.25.2 

答えて

0

double (s.time_since_epoch().count()) 

説明ラインを削除します。 Cythonだけの機能double get_time()が存在することを知っている必要があります - それが提供され、実装(について知っている必要はありません。あなたのC + +コードで)。したがって、Cythonの実装を書き直す必要はありません。


残りのコードを詳しく見ていないので、そこにも問題がある可能性があります。しかし、いくつかの小さなコメント:コンストラクタで

if self._os_time_service_ptr == NULL: 
    raise MemoryError() 

割り当てではなくNULLを返す(とCythonのそのMemoryErrorに自動変換する)よりも、失敗した場合に近代的なC++はstd::bad_allocを発生させますので、これは不要です。それはNULLを削除しても安全ですので、デストラクタ

if self._os_time_service_ptr != NULL: 

は不要です。これらのどちらも問題を引き起こすことはありません。