अंतिम अद्यतनCython और fortran - कैसे f2py
यह सवाल है कि कैसे एक setup.py
कि एक cython मॉड्यूल जो FORTRAN कोड सीधे पहुंचता है, तो सी चाहेंगे संकलन होगा लिखने के बारे में है के बिना एक साथ संकलित करने के लिए। यह समाधान के लिए एक लंबी और कठिन यात्रा थी, लेकिन पूर्ण गड़बड़ संदर्भ के लिए नीचे शामिल है।
मूल प्रश्न
मैं एक विस्तार है जो एक Cython फ़ाइल है, जो कुछ ढेर स्मृति सेट और fortran कोड को पास कर देता है, और एक fortran फ़ाइल है, जो एक सम्मानित वर्ष मॉड्यूल है कि मैं क्या है अगर मैं कर सकता हूं तो पुनर्मूल्यांकन से बचने के लिए।
.pyx
फ़ाइल सेल्सियस के लिए ठीक संकलित, लेकिन cython संकलक निम्न त्रुटि के साथ .f90
फ़ाइल पर chokes:
$ python setup.py build_ext --inplace
running build_ext
cythoning delaunay/__init__.pyx to delaunay/__init__.c
building 'delaunay' extension
error: unknown file type '.f90' (from 'delaunay/stripack.f90')
यहाँ (के शीर्ष आधा) मेरी सेटअप फ़ाइल:
from distutils.core import setup, Extension
from Cython.Distutils import build_ext
ext_modules = [
Extension("delaunay",
sources=["delaunay/__init__.pyx",
"delaunay/stripack.f90"])
]
setup(
cmdclass = {'build_ext': build_ext},
ext_modules = ext_modules,
...
)
नोट: मूल रूप से फोर्ट्रान फ़ाइल का स्थान गलत तरीके से निर्दिष्ट किया गया था (निर्देशिका उपसर्ग के बिना) लेकिन यह ठीक होने के ठीक उसी तरह से टूट जाता है।
बातें मैं कोशिश की है:
मैं this पाया, और fortran संकलक के नाम पर गुजर करने की कोशिश की (यानी gfortran) इस तरह:
$ python setup.py config --fcompiler=gfortran build_ext --inplace
usage: setup.py [global_opts] cmd1 [cmd1_opts] [cmd2 [cmd2_opts] ...]
or: setup.py --help [cmd1 cmd2 ...]
or: setup.py --help-commands
or: setup.py cmd --help
error: option --fcompiler not recognized
और मैं भी कोशिश की है --inplace
को हटाकर, यदि समस्या थी (यह शीर्ष त्रुटि संदेश के समान नहीं था)।
तो, मैं इस किले को कैसे संकलित करूं? क्या मैं इसे .o
में खुद को हैक कर सकता हूं और इसे जोड़ने से दूर हो सकता हूं? या is this a bug in Cython, जो मुझे preutocessor के साथ distutils reimplement या चारों ओर हैक करने के लिए मजबूर करेगा?
अद्यतन
तो, numpy.distutils
संकुल बाहर चेक करने के बाद, मैं थोड़ा अधिक समस्या को समझते हैं। ऐसा लगता है आप के लिए
- उपयोग cython है कि फ़ाइलें ग CPython को .pyx फ़ाइलों को कनवर्ट करने,
- फिर एक
Extension
/setup()
संयोजन, fortran का समर्थन करता है किnumpy
की तरह इस्तेमाल करते हैं।
इस की कोशिश की है, मेरी setup.py
अब इस तरह दिखता है:
from numpy.distutils.core import setup
from Cython.Build import cythonize
from numpy.distutils.extension import Extension
cy_modules = cythonize('delaunay/sphere.pyx')
e = cy_modules[0]
ext_modules = [
Extension("delaunay.sphere",
sources=e.sources + ['delaunay/stripack.f90'])
]
setup(
ext_modules = ext_modules,
name="delaunay",
...
)
(ध्यान दें, कि मैं भी मॉड्यूल थोड़ा की पुनर्संरचना की है के बाद से मालूम होता है एक __init__.pyx
की अनुमति नहीं है ...)
अब वह जगह है जहां चीजें छोटी और मंच-निर्भर हो जाती हैं। मेरे पास दो परीक्षण सिस्टम उपलब्ध हैं - एक मैक ओएस एक्स 10।6 (हिम तेंदुए), मैकपोर्ट पायथन 2.7 का उपयोग करके, और एक मैक ओएस एक्स 10.7 (शेर) सिस्टम पायथन 2.7 का उपयोग कर।
Snow Leopard पर, निम्न लागू होगा:
इसका मतलब है कि मॉड्यूल compiles (हुर्रे!) (हालांकि वहाँ numpy के लिए कोई --inplace
, ऐसा लगता है, इसलिए मैं पूरे सिस्टम पर परीक्षण मॉड्यूल स्थापित करने के लिए किया था:/
>>> import delaunay
Traceback (most recent call last):
File "<input>", line 1, in <module>
File "<snip>site-packages/delaunay/__init__.py", line 1, in <module>
from sphere import delaunay_mesh
ImportError: dlopen(<snip>site-packages/delaunay/sphere.so, 2): no suitable image found. Did find:
<snip>site-packages/delaunay/sphere.so: mach-o, but wrong architecture
और शेर पर, मैं एक संकलन त्रुटि मिलती है, एक नहीं बल्कि भ्रामक देख संकलन लाइन निम्नलिखित:) लेकिन मैं अभी भी एक दुर्घटना import
पर इस प्रकार प्राप्त
gfortran:f77: build/src.macosx-10.7-intel-2.7/delaunay/sphere-f2pywrappers.f
/usr/local/bin/gfortran -Wall -arch i686 -arch x86_64 -Wall -undefined dynamic_lookup -bundle build/temp.macosx-10.7-intel-2.7/delaunay/sphere.o build/temp.macosx-10.7-intel-2.7/build/src.macosx-10.7-intel-2.7/delaunay/spheremodule.o build/temp.macosx-10.7-intel-2.7/build/src.macosx-10.7-intel-2.7/fortranobject.o build/temp.macosx-10.7-intel-2.7/delaunay/stripack.o build/temp.macosx-10.7-intel-2.7/build/src.macosx-10.7-intel-2.7/delaunay/sphere-f2pywrappers.o -lgfortran -o build/lib.macosx-10.7-intel-2.7/delaunay/sphere.so
ld: duplicate symbol _initsphere in build/temp.macosx-10.7-intel-2.7/build/src.macosx-10.7-intel-2.7/delaunay/spheremodule.o ldand :build /temp.macosx-10.7-intelduplicate- 2.7symbol/ delaunay/sphere.o _initsphere in forbuild architecture /i386
temp.macosx-10.7-intel-2.7/build/src.macosx-10.7-intel-2.7/delaunay/spheremodule.o and build/temp.macosx-10.7-intel-2.7/delaunay/sphere.o for architecture x86_64
अब हम यहां विवरणों को पूरा करने से पहले बस एक पल वापस कदम उठाएं। सबसे पहले, मुझे पता है कि 64-बिट मैक ओएस एक्स में आर्किटेक्चर क्लैश पर सिरदर्द का एक गुच्छा है; मुझे हिम तेंदुए मशीन पर काम कर रहे मैकपोर्ट पायथन (सिस्टम पायथन 2.6 से अपग्रेड करने के लिए) बहुत मुश्किल काम करना पड़ा। मुझे यह भी पता है कि जब आप gfortran -arch i686 -arch x86_64
देखते हैं तो आप अपने कंपाइलर में मिश्रित संदेश भेज रहे हैं। वहाँ प्लेटफार्म-विशिष्ट समस्याओं को दफन कर रहे हैं, कि हमें इस प्रश्न के संदर्भ में चिंता करने की आवश्यकता नहीं है।
लेकिन सिर्फ इस लाइन को देखो: gfortran:f77: build/src.macosx-10.7-intel-2.7/delaunay/sphere-f2pywrappers.f
numpy क्या कर रहा है ?! मुझे इस बिल्ड में किसी भी f2py सुविधाओं की आवश्यकता नहीं है! मैंने वास्तव में से बचने के लिए एक साइथन मॉड्यूल लिखा है ताकि मुझे f2py की पागलपन से निपटने के लिए (मुझे 4 या 5 आउटपुट वैरिएबल, साथ ही न तो इन-न-आउट तर्कों की आवश्यकता हो - इनमें से कोई भी f2py में अच्छी तरह से समर्थित नहीं है।) I बस इसे .c
->.o
, और .f90
->.o
संकलित करना और उन्हें लिंक करना चाहते हैं। अगर मैं जानता हूं कि सभी प्रासंगिक शीर्षलेखों को कैसे शामिल किया जाए तो मैं खुद को इस कंपाइलर लाइन को लिख सकता हूं।
कृपया मुझे बताएं कि मुझे इसके लिए अपना खुद का मेकफ़ाइल लिखने की आवश्यकता नहीं है ... या कि फोर्टन को (आउटपुट-संगत) सी का अनुवाद करने का एक तरीका है, इसलिए मैं कभी भी pfthon को .f90 एक्सटेंशन (जो पूरी समस्या को हल करता है।) ध्यान दें कि f2c
इसके लिए उपयुक्त नहीं है क्योंकि यह केवल F77 पर काम करता है और यह एक और आधुनिक बोली है (इसलिए .f90
फ़ाइल एक्सटेंशन)।
अद्यतन 2 निम्नलिखित बैश स्क्रिप्ट खुशी से संकलन और जगह में कोड लिंक करेगा:
PYTHON_H_LOCATION="/opt/local/Library/Frameworks/Python.framework/Versions/2.7/include/python2.7/"
cython sphere.pyx
gcc -arch x86_64 -c sphere.c -I$PYTHON_H_LOCATION
gfortran -arch x86_64 -c stripack.f90
gfortran -arch x86_64 -bundle -undefined dynamic_lookup -L/opt/local/lib *.o -o sphere.so
कैसे एक setup.py के साथ संगत हैक इस तरह का बनाने के लिए पर कोई सलाह? मैं इस मॉड्यूल स्थापित करने कोई भी ढूंढ जाना है नहीं करना Python.h
मैन्युअल ...
फोरट्रान समर्थन 'numpy' से आते हैं लगता है। शायद आप आयात कर सकते हैं [ 'numpy.distutils.extension.Extension'] (http://www.scipy.org/doc/numpy_api_docs/numpy.distutils.extension.html) के बजाय' distutils.core.Extension' की। //docs.scipy: – MvG
भी [NumPy distutils उपयोगकर्ता गाइड] (https://github.com/numpy/numpy/blob/master/doc/DISTUTILS.rst.txt) और [पैकेजिंग संदर्भ] (http पढ़ें। org/doc/numpy-1.6.0/संदर्भ/distutils.html)। – MvG
क्या आपके पास gfortran इंस्टॉल है? आपको वास्तव में कुछ फोरट्रान कंपाइलर चाहिए, यह वास्तव में आवश्यक है। –