首页 \ 问答 \ 如果抛出异常,则使extern C ++函数返回消息(Make extern C++ function return a message if an exception is thrown)

如果抛出异常,则使extern C ++函数返回消息(Make extern C++ function return a message if an exception is thrown)

我想让我的extern C ++函数在发生异常时返回一条消息。 像这样的东西:

extern "C" __declspec(dllexport) const char* __stdcall Calculate(double &result, double a, double b) 
{
    try
    {
        result = InternalCalculation(a, b);
    }
    catch(std::invalid_argument& e)
    {
        return e.what();
    }
    return "";
}


double InternalCalculation(double a, double b)
{
    if(a < b)
    {
        const char* err = "parameters error!";
        throw std::invalid_argument(err);
    }
    return sqrt(a - b);
}

另一方面,我从我的C#程序调用该函数,我想在MessageBox显示错误:

[DllImport(@"MyDll.dll", EntryPoint = "Calculate")]
private static extern IntPtr Calculate(out double result, double a, double b);

private void Calculate()
{
    IntPtr err;     
    double result = 0;
    err = Calculate(out result, out 2, out 3);
    var sErr = Marshal.PtrToStringAnsi(err);
    if (string.IsNullOrEmpty(sErr))
        MessageBox.Show(sErr);
    ...
}

不幸的是,它不起作用.. MessageBox只显示随机字符。

我很惊讶因为如果我更换:

return e.what();

通过:

const char* err = "parameters error!";
return err;

然后“参数错误!” 将在C#代码的消息框中正确显示。 erre.what()都是相同的类型( const char* ),所以e.what()有什么问题?


I would like to make my extern C++ function return a message when an exception occurs. Something like this:

extern "C" __declspec(dllexport) const char* __stdcall Calculate(double &result, double a, double b) 
{
    try
    {
        result = InternalCalculation(a, b);
    }
    catch(std::invalid_argument& e)
    {
        return e.what();
    }
    return "";
}


double InternalCalculation(double a, double b)
{
    if(a < b)
    {
        const char* err = "parameters error!";
        throw std::invalid_argument(err);
    }
    return sqrt(a - b);
}

On the other hand, I call the function from my C# program and I would like to show error in a MessageBox:

[DllImport(@"MyDll.dll", EntryPoint = "Calculate")]
private static extern IntPtr Calculate(out double result, double a, double b);

private void Calculate()
{
    IntPtr err;     
    double result = 0;
    err = Calculate(out result, out 2, out 3);
    var sErr = Marshal.PtrToStringAnsi(err);
    if (string.IsNullOrEmpty(sErr))
        MessageBox.Show(sErr);
    ...
}

Unfortunately, it doesn't work.. the MessageBox just shows random characters.

I'm surprised because if I replace:

return e.what();

by:

const char* err = "parameters error!";
return err;

Then "parameters error!" will be shown correctly in the messagebox of the C# code. Both err and e.what() are the same type (const char*), so what's wrong with e.what()??


原文:https://stackoverflow.com/questions/18162575
更新时间:2023-02-21 07:02

最满意答案

这似乎是一个非常奇怪的方式来做你想做的事情。

做你所提议的“git”方式应该是:

$ git checkout -b edge
... #make your modifications for the port.
$ git commit -m'ported plugins to rails edge' -a
$ git checkout master # original code is there untouched
$ git checkout edge # ported code is there just as you commited it.

从那里取决于你的目标是什么,你可以:

$ git checkout master # make sure you are on the master branch
$ git merge edge # merge the edge branch into master
... # fix any errors
$ git branch -d edge # remove the edge branch since you don't need it anymore.

或保持两个分支。 一个移植到边缘,另一个移植。 这可能不是你想要的。 Git中的分支既便宜又容易,完成后可以将它们丢弃。


That seems like a really strange way to do what you intended.

The more "git" way of doing what you proposed would have been to:

$ git checkout -b edge
... #make your modifications for the port.
$ git commit -m'ported plugins to rails edge' -a
$ git checkout master # original code is there untouched
$ git checkout edge # ported code is there just as you commited it.

From there depending on what you're goal is you can:

$ git checkout master # make sure you are on the master branch
$ git merge edge # merge the edge branch into master
... # fix any errors
$ git branch -d edge # remove the edge branch since you don't need it anymore.

Or maintain two branches. One ported to edge, the other the unported. This is probably not what you want. Branches in git are cheap and easy and is perfectly acceptable to throw them away when you are done.

相关问答

更多
  • 这是插图中的一个错误。 在插图中交换c2b9e和87ab2,它是正确的。 This is a bug in the illustration. Swap c2b9e and 87ab2 in the illustration and it's correct.
  • 您的日志记录逻辑正在执行两个sqlite_step()操作,这最多会产生误导。 而是捕获第一个sqlite_step()调用的返回码并报告该值: int rc = sqlite3_step(statement); if (rc == SQLITE_OK) { NSLog(@"Food added."); } else { NSLog(@"ERROR: Failed to add food!: %d", rc); } 您需要将此逻辑扩展到代码中的所有sqlite_xxx()调用。 I fo ...
  • 你有一个相当顺序的开发周期,所以你是对的:那里不需要大量的功能分支。 一个简单的模型: *--*--*--*---* (master, for prod) \ / *--*--*--* (dev, for current development) 问题是: 如果prod(' master ',实时网站)中存在错误,您可以在dev分支上修复它并包含正在进行的任何开发吗? 因为如果你不能,那就意味着你对master有所改变必须立即在dev上合并。 如果快速完成修复,您甚至不需 ...
  • 您将无法在默认时间轴上追溯引入1.1.3作为变更集,您可以期望的最佳方案如下: 在您发布1.1.2的位置更新回默认值 分支出1.1.3并提交 默认情况下将其与1.1.2标记合并,这将在默认分支上创建另一个头,与您正在处理的1.2时间轴平行 标记为1.1.3并发布 将这个新头部合并到前一个头部,将错误修复程序加入到1.2.x中 警告 :我在测试时发现的一件事是,当我将1.1.3默认内容合并到1.2.0默认内容时,必须合并.hgtags 。 由于标签总是从最末端的变更集中读取(我可能在这里错了),这可能表明这不 ...
  • 这似乎是一个非常奇怪的方式来做你想做的事情。 做你所提议的“git”方式应该是: $ git checkout -b edge ... #make your modifications for the port. $ git commit -m'ported plugins to rails edge' -a $ git checkout master # original code is there untouched $ git checkout edge # ported code is there ...
  • 好吧,这不是真正的VCS问题,这首先是体系结构问题 - 如何构建和构建应用程序,以便能够根据需要将特定用例交付给每个医院,同时还能够正如你的建议,修复commom代码中的错误。 我想可以肯定地说,如果你按照图像中建议的模型进行操作,你将无法始终如一地有效地这样做。 你最终得到的是许多不同的,离散的应用程序,即使它们在某些时候来自一组通用代码,也必须单独维护。 它很难做出更好的概括, 但我想到的方式将是以下几点: 首先,您需要一个核心应用程序(或一组应用程序或一组应用程序库),这些将构成任何交付系统的基础,因 ...
  • 您可以将onConfigurationChanged添加到Application类。 @Override public void onConfigurationChanged(Configuration newConfig) { super.onConfigurationChanged(newConfig); if (newConfig.locale != null) { Locale locale = new ...
  • 我刚刚遇到同样的问题。 我建议从发布分支创建一个普通的分支。 在那里进行修复并为该分支创建一个pull请求以合并到release分支。 这是使用普通的分支和合并命令,而不是Git Flow命令。 步骤详情如下: 结帐发布/ 2017.05.24分支。 2017.05.24是发布分支的名称。 执行branch命令并将其命名为“release2017.05.24 - 修复原因”。 这将显示分支存在的原因(对于发布修复)。 进行更改,提交,将更改推送到服务器(将分支推送到源)。 在您的服务器中,为您的分支创建一个 ...
  • 我实际做的只是在@JoshH建议的where语句中添加一个空格。 public void loadQuestions() { try { String sql = "select * from " + hommer.getSelectedItem() + " where id= ?"; pst = conn.prepareStatement(sql); ...
  • 一个很好的参考(我在“ 你应该何时分支 ”中提到)是: “软件如何演变”的第7章 (pdf) 来自Practical Perforce(Laura WINGERD - O'Reilly):在不同类型的分支之间合并工作流程是一个很好的介绍(VCS不可知)。 A good reference (that I mention in "When should you branch") is: Chapter 7 of "How Software Evolves" (pdf) From Practical Perfo ...

相关文章

更多

最新问答

更多
  • 获取MVC 4使用的DisplayMode后缀(Get the DisplayMode Suffix being used by MVC 4)
  • 如何通过引用返回对象?(How is returning an object by reference possible?)
  • 矩阵如何存储在内存中?(How are matrices stored in memory?)
  • 每个请求的Java新会话?(Java New Session For Each Request?)
  • css:浮动div中重叠的标题h1(css: overlapping headlines h1 in floated divs)
  • 无论图像如何,Caffe预测同一类(Caffe predicts same class regardless of image)
  • xcode语法颜色编码解释?(xcode syntax color coding explained?)
  • 在Access 2010 Runtime中使用Office 2000校对工具(Use Office 2000 proofing tools in Access 2010 Runtime)
  • 从单独的Web主机将图像传输到服务器上(Getting images onto server from separate web host)
  • 从旧版本复制文件并保留它们(旧/新版本)(Copy a file from old revision and keep both of them (old / new revision))
  • 西安哪有PLC可控制编程的培训
  • 在Entity Framework中选择基类(Select base class in Entity Framework)
  • 在Android中出现错误“数据集和渲染器应该不为null,并且应该具有相同数量的系列”(Error “Dataset and renderer should be not null and should have the same number of series” in Android)
  • 电脑二级VF有什么用
  • Datamapper Ruby如何添加Hook方法(Datamapper Ruby How to add Hook Method)
  • 金华英语角.
  • 手机软件如何制作
  • 用于Android webview中图像保存的上下文菜单(Context Menu for Image Saving in an Android webview)
  • 注意:未定义的偏移量:PHP(Notice: Undefined offset: PHP)
  • 如何读R中的大数据集[复制](How to read large dataset in R [duplicate])
  • Unity 5 Heighmap与地形宽度/地形长度的分辨率关系?(Unity 5 Heighmap Resolution relationship to terrain width / terrain length?)
  • 如何通知PipedOutputStream线程写入最后一个字节的PipedInputStream线程?(How to notify PipedInputStream thread that PipedOutputStream thread has written last byte?)
  • python的访问器方法有哪些
  • DeviceNetworkInformation:哪个是哪个?(DeviceNetworkInformation: Which is which?)
  • 在Ruby中对组合进行排序(Sorting a combination in Ruby)
  • 网站开发的流程?
  • 使用Zend Framework 2中的JOIN sql检索数据(Retrieve data using JOIN sql in Zend Framework 2)
  • 条带格式类型格式模式编号无法正常工作(Stripes format type format pattern number not working properly)
  • 透明度错误IE11(Transparency bug IE11)
  • linux的基本操作命令。。。