質問をすることでしか得られない、回答やアドバイスがある。

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

新規登録して質問してみよう
ただいま回答率
85.48%
DLL

DLL(Dynamic Link Library)とは、他のモジュールからも使用する事が出来る、関数とデータが格納されているモジュールのことです。

C++/CLI

C++/CLIは、.NET Frameworkの共通言語基盤であるCLI向けにC++を拡張したプログラム言語です。前身のC++マネージ拡張と比較するとシンプルで分かりやすい構文になっており、高い可読性を持ちます。

Q&A

0回答

1223閲覧

C#からC++の関数をクラスライブラリ経由で利用するできない

Soogle44

総合スコア8

DLL

DLL(Dynamic Link Library)とは、他のモジュールからも使用する事が出来る、関数とデータが格納されているモジュールのことです。

C++/CLI

C++/CLIは、.NET Frameworkの共通言語基盤であるCLI向けにC++を拡張したプログラム言語です。前身のC++マネージ拡張と比較するとシンプルで分かりやすい構文になっており、高い可読性を持ちます。

0グッド

1クリップ

投稿2022/01/18 04:52

編集2022/01/20 08:00

前提・実現したいこと

GUIをC#、処理をC++で行うような画像処理のソフトを開発しようとしています。
その際、intなどの変数は受け渡しできるのですが、Mat型の変数の受け渡しができず困っています。

発生している問題・エラーメッセージ

C++の関数をC#で使う方法はいくつかあると思いますが、こちらのリンクを参考に、C++のdllをC#から使うという構成で作成しました。
はじめに確認として、C#からMat型の変数を受け取り、その変数をそのままreturnするような処理をしようとしましたが、以下のようなハンドルされない例外がありつまずいています。

System.InvalidOperationException:'この型は、その階層内にComVisible(false)の親を含んでいます。このため、IDispatchのQueryInterfacec呼び出し、またはクラスインターフェースは許可されません。'

該当のソースコード

c#

1using System.Runtime.InteropServices; 2using OpenCvSharp; 3 4namespace Application 5{ 6 public partial class MainWindow : System.Windows.Window 7 { 8 [DllImport( "Library.dll" )] 9 static extern Mat Test(Mat image); 10 11 public MainWindow() 12 { 13 InitializeComponent(); 14 Mat image = Cv2.Imread("test.jpg"); 15 Cv2.Imshow("image", image); 16 Mat image2 = Test(image); 17 Cv2.Imshow("image2", image2); 18 } 19 } 20}

c++

1//library.h 2#pragma once 3#include <opencv2/opencv.hpp> 4 5extern "C" 6{ 7 __declspec( dllexport ) cv::Mat Test(cv::Mat image); 8} 9 10//library.cpp 11#include <iostream> 12#include "library.h" 13 14cv::Mat Test(cv::Mat image) 15{ 16 return image; 17}

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

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

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

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

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

Soogle44

2022/01/19 03:19

返信遅れて申し訳ございません、ありがとうございます。 確認してみます。
KOZ6.0

2022/01/20 01:09

C++/CLI にしたなら、OpenCvSharp を参照設定して使うだけでは?
KOZ6.0

2022/01/20 01:35 編集

System.String^ は System.Runtime.InteropServices.Marshal クラスを使って BSTR に変換できます。 そこから std:string に変換すれば良いと思います。 Marshal.StringToBSTR(String) メソッド https://docs.microsoft.com/ja-jp/dotnet/api/system.runtime.interopservices.marshal.stringtobstr?view=netframework-4.8 Marshal.PtrToStringBSTR(IntPtr) メソッド https://docs.microsoft.com/ja-jp/dotnet/api/system.runtime.interopservices.marshal.ptrtostringbstr?view=netframework-4.8 なんだか明後日の方向に向かっているような気がします。メモリの解放もれに気を付けてください。
Soogle44

2022/01/20 01:32

ありがとうございます。 情報がぬけていて申し訳ございませんが、最終的にはc++の物体検出プログラムの活用をしたいと考えており、その前段階として簡単なopencvの処理をc++側でさせようとしています。
Soogle44

2022/01/20 01:34

ありがとうございます。 確認してみます。
Soogle44

2022/01/20 01:59

imshowの引数にSystem::String^からstd::stringに変更したものを指定することを試してみましたが、同様にアンマネージドだからマネージドで書きましょう、となっています。 ```c++ void OpenCVLibrary::ProcMat::test() { System::String^ sys_name = "dog.jpg"; std::string std_name = msclr::interop::marshal_as<std::string>(sys_name); cv::mat = imread(std_name); cv::imshow("test", mat); cv::waitKey(0); } ``` 申し訳ございません、見当はずれなことをしていましたらご指摘ください。
KOZ6.0

2022/01/20 02:26

marshal_as なんてあったんですね。 「同様にアンマネージドだからマネージドで書きましょう」ってどういう意味ですか?
Soogle44

2022/01/20 02:34

ありがとうございました。 ハンドルされない例外(System.Runtime.InteropServices.SEHException: )が表示されたときに Inspection of unmanaged type 'std::basic_string<char,std::char_traits<char>,std::allocator<char> >*' requires unmanaged debugging to be enabled. Please set the debugger type to 'Mixed' and try again と表示されています。書かれている通りデバッガーのモードを変更しても変化はありませんでした。 ![デバッグ時の表示](https://ddjkaamml8q8x.cloudfront.net/questions/2022-01-20/1ca9e509-7e40-4652-a9f4-fe5d88dbd7c7.png)
KOZ6.0

2022/01/20 02:59

std_name でエラーが出てますね。 marshal_as の使い方ってこれでいいんですか?
KOZ6.0

2022/01/20 03:42

C++/CLR の役割ですが、あれこれ機能を持たせようとするから問題なので C++ のライブラリがエクスポートした関数と C# との橋渡しに留めてみては?
KOZ6.0

2022/01/20 03:45

あ、32bit/64bit は大丈夫なんでしょうか?
KOZ6.0

2022/01/20 03:52

imread の引数は st:string なので、OpenCV ですよね? cv::imgshow って OpenCVSharp じゃないですか?
Soogle44

2022/01/20 04:07

ありがとうございます。 64bitで統一していてそれは問題なさそうです。 opencvでもcv::imshowがあるので大丈夫かなと思います。 気がかりなのがimreadでstd::stringを使うのは問題なくて、imshowで使うときに例外が発生することなんですよね、おそらくメモリを参照しようとしたらうまく書き込めていなかったといったことなのですが..
KOZ6.0

2022/01/20 04:15

>opencvでもcv::imshowがあるので大丈夫かなと思います。 確実ですか?エラーメッセージが .NET のものなので気になります。
Soogle44

2022/01/20 04:29

ありがとうございます。 ``` #include <opencv2/opencv.hpp> int main() { cv::Mat img; img = cv::imread("suwawachan.jpg"); cv::imshow("title", img); cv::waitKey(0); return 0; } ``` [こちら](https://swallow-incubate.com/archives/blog/20181221/)からコピーしてきましたがこのようにかけるのでopencv(c++)でもcv:imshowは問題なさそうです。
KOZ6.0

2022/01/20 04:37

上のコードは imread, 下のコードは c:imread になってますね。 上のコードはなぜ cv:imread じゃないんですか? よくわからないですし、明後日の方向に向かってるようなので撤退します。
Soogle44

2022/01/20 04:48

ありがとうございます。 承知しました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだ回答がついていません

会員登録して回答してみよう

アカウントをお持ちの方は

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問