Accessing a Matrix

In the code below I get error indicating error in accessing one-dimentional matrix

This code was working OK but I wanted to relocate the function that includes this code.

Question:
What is the proper format for accessing matrix below?
x = Matrix( 1, 10, 0);
value = x[0][5]; OR value = x[5];

What is the scope of a matrix?

    for( b = 1; b <= 12; b++ )	   							
    {
        //calculate rectangle coordinates
        MomGZero		= MomGZeroMx[0][b];         // <<<< ====  PROBLEM LINE
		//
        x1		= 2 * X_BlankSpace + FirstBar_Offset  + ( b - 1 ) * Monthwidth - 3;
        y1		= yzero;
        x2		= int( x1 + ( num_Years ) * Barwidth );
        y2		= y1 - ( AvgMonthMomMx[0][b]  * Y_scalemult );

        //
        //Compute x-center value for prior month											
        if( b == 1 ) bb = 12;
		//
        x3		= 2 * X_BlankSpace + FirstBar_Offset  + ( bb ) * Monthwidth - 3;
        x3		= ( x1 + x2 ) / 2;
        //
        if( b > 0 AND b < 12 )	select_month 	= Curr_Month + 1;
        else select_month = 1;

        if( select_month	== b )
        {
            GfxSelectSolidBrush( colorblue );
            GfxSelectPen( colorblue, width = 2, penstyle = 0 );
        }
        else
        {
            if( MomGZero >= 80 )	GfxSelectSolidBrush( colorgreen );		// 80% of annual momentums in given month are greater than zero
            else
                GfxSelectSolidBrush( colorpalegreen );					// color of month bar

            GfxSelectPen( colorblue, width = 1, penstyle = 0 );			// Lines around month bar
        }

        //
        GfxRectangle( x1, y1, x2, y2 );  								// Plot Month averaged momentum
    }
`

As message says - This variable is NOT A MATRIX, it is just an 1D array.

Use this:


it is better way to understand your own code

You can use

_TRACE("Variable type " + typeof( MomGZeroMx ) );

and it will clearly show you that the variable you think is matrix is NOT a matrix.

I’ve heard of similar “problem” and it turned out that the user lost track of what he wrote himself and simply overwritten the variable with regular array somewhere else in the code.

Bottom line: use debugger and use _TRACE.

Hi everybody.

I have a strange problem when using the MxGetBlock function.
The following code generates an error "Incorrect start/end row/column" on the line calculating Y2 while Y1, Y3 and Y4 do not generate any error.
Any explanation?

date_start1 = Year() == 2018 AND Month() == 1 AND Month() != Ref(Month(), -1); 
date_start2 = Year() == 2018 AND Month() == 2 AND Month() != Ref(Month(), -1);	

// Convert dates to bars
start1 = LastValue(ValueWhen(date_start1, BarIndex(), 1));
start2 = LastValue(ValueWhen(date_start2, BarIndex(), 1));
start3 = LastValue(ValueWhen(date_start2, BarIndex() - 1, 1));

// Generate matrixes
X = Matrix(1, BarCount, 1);

Y1 = MxGetBlock(X, 0, 0, start1, start2, False);			// OK
Y2 = MxGetBlock(X, 0, 0, start1, start2 - 1, False);		// Error
Y3 = MxGetBlock(X, 0, 0, start1, BarCount - 1, False);		// OK
Y4 = MxGetBlock(X, 0, 0, start1, start3, False);			// OK

There is not anything strange there. Just trace. Have you?

If you click apply button of editor then start1, start2, start3 become zero.
Zero minus one is...? Right, it is "-1". Indexes (of rows and columns) have to be equal or larger than zero (and lower than defined array sizes).

So you assume that start2 - 1 would always be positive. But as been told by T.J. many times do NOT assume. http://www.amibroker.com/kb/2014/09/22/do-not-make-assumptions-on-number-of-bars/

YOU have to ensure that your program(s) run without error on every occasion. It is your responsibilty.

BTW this one will not become negative.

Max(0, start2 - 1)	

Thank you. It works using max function.
I have had checked my numbers with printf and they were largely positive.
But I did not think about the reset of the variables when applying the formula.

I am getting insane with those matrices!!!
Consider the following code:

SetBarsRequired(sbrAll, sbrAll);

x1 = C - ref(C, -1);
x2 = C - Ref(C, -2);

MX = Matrix(2, barcount, 0);
MX = MxSetBlock( MX, 0, 0, 0, BarCount - 1, x1); 
MX = MxSetBlock( MX, 1, 1, 0, BarCount - 1, x2); 

rowX = MxGetSize(MX, 0);			// Debugger shows rowX = 2
colX = MxGetSize(MX, 1);			// Debugger shows rowY = 4625

a1 = MX[0][199];
b1 = MX[1][199];
a2 = MX[0][200];
b2 = MX[1][200];

z = 1;




MX1 = MxGetBlock(MX, 0, 1, 50, 199);

MX2 = MxGetBlock(MX, 0, 1, 50, 200);

Using the debugger, I put a break point on the line "z = 1".The dimension of the matrix is correct and I can access to col. 199 and 200.
image

Then when I want to apply my formula, I get 3 errors on the lines that are trying to access col 200.
image

What am I doing wrong???

Have you actually read the link posted 2 posts above (carefully)??

The Barcount in editor is limited to 200 bars (i.e. if using verify syntax or clicking apply button)!
So your index is exceeding Barcount if larger than 199! Got nothing to do with matrices. You wil get same error with 1-dim arrays.

2018-03-27_233756


_TRACEF( "Barcount: %g", BarCount );

2018-03-27_233847


Now, these two ones will not report error

SetBarsRequired(sbrAll, sbrAll);

x1 = C - ref(C, -1);
x2 = C - Ref(C, -2);

MX = Matrix(2, barcount, 0);
MX = MxSetBlock( MX, 0, 0, 0, BarCount - 1, x1); 
MX = MxSetBlock( MX, 1, 1, 0, BarCount - 1, x2); 

rowX = MxGetSize(MX, 0);			// Debugger shows rowX = 2
colX = MxGetSize(MX, 1);			// Debugger shows rowY = 4625

if( Status( "actionex" ) != actionExEditVerifyFormula ) {

	a1 = MX[0][199];
	b1 = MX[1][199];
	a2 = MX[0][200];
	b2 = MX[1][200];

	z = 1;

	MX1 = MxGetBlock(MX, 0, 1, 50, 199);
	MX2 = MxGetBlock(MX, 0, 1, 50, 200);
}
SetBarsRequired(sbrAll, sbrAll);

x1 = C - ref(C, -1);
x2 = C - Ref(C, -2);

MX = Matrix(2, barcount, 0);
MX = MxSetBlock( MX, 0, 0, 0, BarCount - 1, x1); 
MX = MxSetBlock( MX, 1, 1, 0, BarCount - 1, x2); 

rowX = MxGetSize(MX, 0);			// Debugger shows rowX = 2
colX = MxGetSize(MX, 1);			// Debugger shows rowY = 4625

if( BarCount > 200 ) {

	a1 = MX[0][199];
	b1 = MX[1][199];
	a2 = MX[0][200];
	b2 = MX[1][200];

	z = 1;

	MX1 = MxGetBlock(MX, 0, 1, 50, 199);
	MX2 = MxGetBlock(MX, 0, 1, 50, 200);
}
1 Like

Actually it rather should be

SetBarsRequired(sbrAll, sbrAll);

x1 = C - ref(C, -1);
x2 = C - Ref(C, -2);

MX = Matrix(2, barcount, 0);
MX = MxSetBlock( MX, 0, 0, 0, BarCount - 1, x1); 
MX = MxSetBlock( MX, 1, 1, 0, BarCount - 1, x2); 

rowX = MxGetSize(MX, 0);			// Debugger shows rowX = 2
colX = MxGetSize(MX, 1);			// Debugger shows rowY = 4625

if( BarCount > 50 && Status( "actionex" ) != actionExEditVerifyFormula ) {

	a1 = MX[0][199];
	b1 = MX[1][199];
	a2 = MX[0][200];
	b2 = MX[1][200];

	MX1 = MxGetBlock(MX, 0, 1, 50, 199);
	MX2 = MxGetBlock(MX, 0, 1, 50, 200);
}

Because it is never assured that barcount will be >50 for every case (see your column startindex within MxGetBlock). So e.g. if some of your symbols have just barcount of 50 you would get error again if using

if(barcount>200)

I was aware of the number of bars of the debugger and it was set to 5000 bars. Nevertheless, the problem with the 200 barrier is present.

Both of your solutions are working. The only inconvenient is that any reference to the matrix created under the if condition have be included within the if condition (i.e. error of the mxGetSize outside the bracket). It might alter the code readibility, but it is a second order issue.

To be sure that I understand correctly the case, is it true to say that the code would work correctly on the current symbol which has a sufficient number of bars but internal processing of the editor/debugger generates an error.

Thanks again for your effort to educate dummy users like me.

image

It is OK now.
Beppe's message has clarified.