🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
MacOS(OSX)

MacOSとは、Appleの開発していたGUI(グラフィカルユーザーインターフェース)を採用したオペレーションシステム(OS)です。Macintoshと共に、市場に出てGUIの普及に大きく貢献しました。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

1回答

3948閲覧

pythonでctypesの利用してc++の関数を呼び出したいが,少し不具合がある.(mac)

Y.kawa

総合スコア12

MacOS(OSX)

MacOSとは、Appleの開発していたGUI(グラフィカルユーザーインターフェース)を採用したオペレーションシステム(OS)です。Macintoshと共に、市場に出てGUIの普及に大きく貢献しました。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2019/11/02 12:18

編集2019/11/02 12:22

初めての投稿です.
markdownもあまり触ったことはなく,至らぬところあるとは思いますがよろしくお願いします.
私のプログラミング歴は,python歴2年,c++歴2週間です.
以下にいろいろまとめてます(書き方は合っているでしょうか...)

macOS:catalina
c++: clang(11.0.0)
python: 3.7.3
ctypes: 1.1.0

それでは本題に入ります.

ctypesを利用してc++の関数を呼び出したい

プログラムを以下の通り作ってみました.
まずはc++でhello.cppを書きました.

c++

1#include <iostream> 2using namespace ::std; 3void hello(){ 4 cout << "Hello" << endl; 5} 6int main(){ 7 hello(); 8}

これをmacのダイナミックライブラリ.dylibとして以下の通りコンパイルしました.

sh

1$ clang++ -dynamiclib -o hello.dylib hello.cpp -std=gnu++14 2$ ls 3hello.cpp hello.dylib

コンパイル自体は問題ないので,pythonでとりあえずmain関数を呼び出すコードとしてctypes_test.py作成しました.

python

1import ctypes 2libc = ctypes.cdll.LoadLibrary("hello.dylib") 3libc.main()

これを実行しました.

sh

1$ python ctypes_test.py 2$ Hello

このようにmain関数は呼び出せますが,次の通りctypes_test.pyを直して,

python

1import ctypes 2import os 3home = os.environ["HOME"] 4os.chdir(home + "/KYTHON/test/ctypes/") 5libc = ctypes.cdll.LoadLibrary("hello.dylib") 6libc.hello()

これをコンパイルすると,

sh

1$ python ctypes_test.py 2$ Traceback (most recent call last): 3 File "ctypes_test.py", line 6, in <module> 4 libc.hello() 5 File "**私のホームディレクトリ**/anaconda3/lib/python3.7/ctypes/__init__.py", line 369, in __getattr__ 6 func = self.__getitem__(name) 7 File "**私のホームディレクトリ**/anaconda3/lib/python3.7/ctypes/__init__.py", line 374, in __getitem__ 8 func = self._FuncPtr((name_or_ordinal, self)) 9AttributeError: dlsym(0x7fc181500f10, hello): symbol not found

となって,hello関数を呼び出せないです.

どうやらctypesがmain関数だけしか認識してくれないようです.
このように,macでのctypesの利用について同じ悩みを抱えている人はいませんか?
または,解決法をご存知の方は教えていたらげると幸いです.

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

自己解決

CでC++を呼び出すときに必要(らしい)な, extern "C"という宣言をすると読み込めるようになりました!

C++

1#include <iostream> 2using namespace ::std; 3 4extern "C" int hello(){ 5 cout << "Hello"<<endl; 6 return 0; 7} 8 9int main(){ 10 hello(); 11}

ただ,何故なのかはわかりません....
これはmacだけのことなのかもわからないです.
他にもいろいろ,情報が知りたいので何か情報があれば教えて欲しいです.

謎が解けました! YouheiSakurai さんありがとうございます!

共有ライブラリの関数を外から呼び出すときには普通「extern "C"」での定義が必要です。そうじゃないと外からhelloという名前で関数を参照しようとしても見つけられなくなります。main()はコンパイラによって暗黙的に「extern "C"」されていたんじゃないでしょうか、たぶん。ちなみに「extern "C"」はmacに限りません。

投稿2019/11/02 13:49

編集2019/11/03 12:18
Y.kawa

総合スコア12

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

YouheiSakurai

2019/11/02 14:12 編集

共有ライブラリの関数を外から呼び出すときには普通「extern "C"」での定義が必要です。そうじゃないと外からhelloという名前で関数を参照しようとしても見つけられなくなります。main()はコンパイラによって暗黙的に「extern "C"」されていたんじゃないでしょうか、たぶん。ちなみに「extern "C"」はmacに限りません。
Y.kawa

2019/11/02 15:46

なるほど、バッチリ理解できました! 勉強になりました。 ありがとうございます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問