user13750697
user13750697

Reputation:

C++ Exception is Caught Late, what may cause this?

I have the following code in main.cpp:

#include <iostream>
#include "Matrix.h"

int main(){
    mtm::Dimensions dim_1(2,3);
    try{
        const mtm::Matrix<int> mat_1 = mtm::Matrix<int>::Diagonal(2,1);
        mtm::Matrix<int> mat_2 = mtm::Matrix<int>::Diagonal(2,-1);
        std::cout<<(-mat_2)(1,1)<<(-mat_2)(2,2)<<std::endl;
    } catch(mtm::Matrix<int>::AccessIllegalElement& e){
        std::cout<<e.what()<<std::endl;
    }
}

while it's supposed to give me the following output:

Mtm matrix error: An attempt to access an illegal element

it returns the following: (notice 1 at the beginning)

1Mtm matrix error: An attempt to access an illegal element

Here is how I have implemented operator<< in Matrix.h:

template<typename T>
std::ostream &operator<<(std::ostream &os, const Matrix<T> &matrix) {
    typename Matrix<T>::const_iterator it_begin = matrix.begin();
    typename Matrix<T>::const_iterator it_end = matrix.end();
    return printMatrix(os, it_begin, it_end, matrix.width());
}

while printMatrix() code is:

template<class ITERATOR_T>
std::ostream& printMatrix(std::ostream& os,ITERATOR_T begin,
                          ITERATOR_T end, unsigned int width){
    unsigned int row_counter=0;
    for (ITERATOR_T it= begin; it !=end; ++it) {
        if(row_counter==width){
            row_counter=0;
            os<< std::endl;
        }
        os <<*it<<" ";
        row_counter++;
    }
    os<< std::endl;
    return os;
}

What may cause this bug and how may I fix it?

Please let me know if anything is missing.

Upvotes: 0

Views: 48

Answers (1)

Bathsheba
Bathsheba

Reputation: 234715

The statement std::cout << (-mat_2)(1,1) << (-mat_2)(2,2) << std::endl; is no more than a shorthand way of writing a chain of function calls.

Prior to C++17, the order of the evaluation of the parameters of the separate functions in the statement is unspecified.

So on some platforms (-mat_2)(1,1) might raise the exception, and on others (-mat_2)(2,2) might raise it.

One solution prior to C++17 is to break up the std::cout into separate statements if you want to control the behaviour more tightly.

From C++17, the order is specified, and the exception must be thrown from (-mat_2)(1,1).

Upvotes: 2

Related Questions