在代码可以执行之前,当我进入函数时引发异常
Exception being raised as I enter into function before code can be executed
和往常一样,我可能在这里遗漏了一些明显的东西。我不能发布整个源代码,因为它与工作有关,但我有一个模板化的Matrix
类,mulMM
(矩阵乘以矩阵)函数和mulMT
函数(矩阵乘以转置矩阵)。它已经存在于代码中。我试图添加一个专门用于单精度浮点值的mulMT
函数。我有一个类似的专门化,mulMM
,它共享相同的前两个函数参数。下面是一些示例代码:
#ifdef TARGET_x86_SSE4
template <>
Matrix<Float>& Matrix<Float>::mulMM (const Matrix<Float>& mat1,
const Matrix<Float>& mat2);
template <>
Matrix<Float>& Matrix<Float>::mulMT (const Matrix<Float>& mat1,
const Matrix<Float>& mat2,
const bool softmax);
#endif // no SSE4: use template generic
template <class BT>
Matrix<BT>& Matrix<BT>::mulMM (const Matrix<BT>& mat1,
const Matrix<BT>& mat2) {
// Function code
}
template <class BT>
Matrix<BT>& Matrix<BT>::mulMT (const Matrix<BT>& mat1,
const Matrix<BT>& mat2,
const bool softmax) {
// Function code
}
然后,在另一个文件中:
#ifdef TARGET_x86_SSE4
template <>
Matrix<Float>& Matrix<Float>::mulMM (const Matrix<Float>& mat1,
const Matrix<Float>& mat2) {
// Function code
}
template <>
Matrix<Float>& Matrix<Float>::mulMT (const Matrix<Float>& mat1,
const Matrix<Float>& mat2,
const bool softmax) {
// Function code
}
当我调用代码时,mulMM正确地提取输入矩阵的值,但是当我调用mulMT时,我得到的是矩阵维数的随机数。使用调试器,我可以看到矩阵在进入时是正确定义的,但是一旦我进入函数,值就都错了。下面是我使用的一些示例代码:
MatrixFloat mA(4, 5);
MatrixFloat mB(5, 4);
// Code to initialize mA and mB's values.
MatrixFloat mR = mR.mulMM(mA, mB)
// This works fine and correctly find the values for the product.
MatrixFloat mC(4, 4)
// Code to initialize mC
mR = mR.mulMT(mC, mC)
// This fails with a memory access error and stepping into the function reveals
// that this seems to be because mC has dimensions of 84376 x 1 or thereabouts
我试过让这两个值变成MT不同。我已经验证过,当我的浮点数的mulMT不存在时,通用的可以工作。我不知道为什么会这样
Edit:为了证明Float专门化中的代码不是问题,我把它注释掉了。一切工作。我取消了代码注释。一切都还在运转。我在想,也许Visual Studio只是搞混了,没有重新编译一些东西。
进一步编辑: OK…这很奇怪。在调试时,当我第一次进入mulMT时,它将我放到const bool softmax) {
行。如果我尝试F10,就会得到异常。如果我按下F11,就会进入ChkStk.asm
。如果我退出那个文件,我就能访问函数内部,一切都被正确分配了。事实上,只要我不重新编译我的测试程序,我就可以按照自己的喜好逐次执行或运行,而不会出现错误。但是,如果我对测试程序进行更改并重新编译,行为就会恢复。
我比开始时更困惑了。
编辑:好吧,两天没有问题,它又出现了。我认为这不像我之前想的那样,涉及到价值观的改变。相反,它是在参数实际实例化之前发生的事情。事情是,我不知道为什么,除此之外,这是我唯一的函数,如果我在进入函数后点击F11
,我就会进入stkchk.asm
。
UnitTest.exe中0x00789adc的第一次异常:0xC0000005:访问违反读取位置0xabababab。是我得到的例外。在函数的前面,我做了一个几乎相同的调用,只是改变了与操作符一起使用的变量。奇怪的是,调用周围的try-catch块并不能防止程序崩溃。
我知道是哪里出了问题。异常确实发生在函数内部。Visual Studio正在优化这个函数,所以除非我在里面有一个断点,否则它会跳过所有的函数。如果函数正常运行,它就正常运行。如果内部有任何异常,则失败。仍然不知道为什么try
catch
块没有捕获它,但我不担心。
感谢大家的努力帮助。谢谢你,@JBL最后是对的。
- 赋予全局变量而不是局部变量优先级的函数 - (异常行为)
- 通过引用从 c++ 函数异常返回对象是否安全
- 智能指针和构造函数异常
- 构造函数C++异常说明符
- boost::archive::text_iarchive构造函数异常
- C++堆栈对象的构造函数异常处理
- 默认构造函数C++异常不会引发吗?
- 重写std的析构函数:异常
- 将向量作为参数(C++)传递时,没有匹配函数异常
- 当函数中静态变量的构造函数异常终止时会发生什么
- 如何:捕获输入函数异常的可变包装函数
- 在c++中,如果基类构造函数异常,则构造函数和析构函数的顺序可以是这样
- noexcept(false)析构函数覆盖所有特殊成员函数'异常规范
- c++重载函数异常规范
- c++ RAII析构函数异常
- 如何捕获构造函数异常
- C++构造函数异常处理
- 捕获构造函数异常的RAII方法
- C++析构函数异常
- Std::unique_ptr::reset和构造函数异常