PDA

View Full Version : Strange issue with print


Grimrandomer
27/09/2013, 11:48 PM
I have the following code:

print("CHECK_TWOPAIRS - START");
for (new _card=1; _card<=13; _card++) {
if (countC[_card-1]==2) {
for (new _subCard=1; _subCard<=13; _subCard++) {
if (_subCard != _card) {
if (countC[_subCard-1]==2) {
return CHECK_TWOPAIRS;
}
}
}
}
}
print("CHECK_TWOPAIRS - END");


Output:

[00:48:21] CHECK_TWOPAIRS - START
[00:48:21] CHECK_TWOPAIRS - END


works a treat, but when i comment out the "print"s:

//print("CHECK_TWOPAIRS - START");
for (new _card=1; _card<=13; _card++) {
if (countC[_card-1]==2) {
for (new _subCard=1; _subCard<=13; _subCard++) {
if (_subCard != _card) {
if (countC[_subCard-1]==2) {
return CHECK_TWOPAIRS;
}
}
}
}
}
//print("CHECK_TWOPAIRS - END");


I get the following crash:

[00:50:55] [debug] Run time error 4: "Array index out of bounds"
[00:50:55] [debug] Accessing element at index 8685052 past array upper bound 4
[00:50:55] [debug] AMX backtrace:
[00:50:55] [debug] #0 00047c28 in ?? () from grimrandomerRoleplay.amx
[00:50:55] [debug] #1 000b81e4 in public OnGameModeInit () from grimrandomerRoleplay.amx


Any thoughts? thanks Grim.

Edit: The test data for both runs is Exactly the same, just to rule it out.

BullseyeHawk
28/09/2013, 01:06 AM
index 8685052
I have a feeling it refers to countC.

Can you post up the new countC[...]; ?

--

The thing is you need to think about the error.
Run time error 4: "Array index out of bounds"
Okay -- We have this error, why? Array index is bigger then the value is able to be settle in.
Example:

new countC[3];

// in a public
for(new countCs = 1; countCs < 99; countCs++) { printf("%d", countC[countCs]); }

It tries to load data that isn't actually stored inside the array, meaning. Past the array bounds.

--

Look at your script as it refers towards OnGameModeInit() in address 000b81e4(well, not an actual address as I remember trought memory editing), I'd guess that for loop is inside the OnGameModeInit().

- But wait, something wierd indeed happens? when I have print on there is no errors.
-- Well, firstly I didn't understand why the heck are you doing [_card-1]. Isn't it easier to do this?:

new countC[14]; // 0 - 13 is used. 14 is a null cell.

for(new _card=0; _card<14; _card++)
{ // starts from 0 and then reaches 13. Not going over to 14 due to '< 14'
if(countC[_card] == 2)
{ // if countC[cell] would equal to integer 2.
for(new _subCard=0; _subCard<14; _subCard++)
{ // starts from 0 and then reaches 13. Not going over to 14 due to '< 14'
if(_subCard != _card)
{ // if #loop2 does NOT equal to #loop1 then continue. (integers of course)
if(countC[_subCard] == 2) return CHECK_TWOPAIRS; // quick way to wrap-up the whole thingy.
}
}
}
}


--

Let's think out of the box for a moment. (This isn't nessesry if you just want it to find one "twopairs" and never continue anymore & if its in the end of the script.)

When we call out the CHECK_TWOPAIRS as a return, it would STOP OnGameModeInit and won't continue anymore.
We don't want that right? Example of what will happen:


OnGameModeInit()
{
// Stuff here before the for loop.
// --> countC loop with the 'return CHECK_TWOPAIRS;'
// More stuff here after loop.
}


Problem is, when you call out a return. ANYWHERE, it will no longer continue to support whats after it. (In short-terms, won't access it cause it would think its job is done)

Insted, for 'for loops' we use: "continue" - if we want it to continue the loop untill it finishes. OR "break" - this will say, "Okay, we found what we want. Let's stop the loop cause we don't want anything else." (<== EXAMPLE) This would basicly stop the whole loop and won't continue anymore.

With this in-mind, I'd guess we should continue like this:

new countC[14]; // 0 - 13 is used. 14 is a null cell.

for(new _card=0; _card<14; _card++)
{ // starts from 0 and then reaches 13. Not going over to 14 due to '< 14'
if(countC[_card] == 2)
{ // if countC[cell] would equal to integer 2.
for(new _subCard=0; _subCard<14; _subCard++)
{ // starts from 0 and then reaches 13. Not going over to 14 due to '< 14'
if(_subCard != _card)
{ // if #loop2 does NOT equal to #loop1 then continue. (integers of course)
if(countC[_subCard] == 2)
{
// Send this over to another checkup script, example: OnFoundTwoPairs(_card, _subCard);
continue; // <== This isn't really needed, cause there is no return.
// or just return continue; // Same as above ^
// break; // If we don't want anything else going on here, let's just stop with break;
// or just return break; // Same as above ^ (not sure about this tho, never tried it out)
}
}
}
}
}


Try out the last pawn snippet I posted up, and tell me the results. You can also debug exactly where does the error happens by using print inside the loop.

Also post what I said in the top of my post, the countC variable of yours.

Grimrandomer
28/09/2013, 02:12 AM
Well, funny thing is, it turned out to be unrelated code:



print("CHECK_TWOPAIRS - START");
for (new _card=1; _card<=13; _card++) {
if (countC[_card-1]==2) {
for (new _subCard=1; _subCard<=13; _subCard++) {
if (_subCard != _card) {
if (countC[_subCard-1]==2) {
return CHECK_TWOPAIRS;
}
}
}
}
}
print("CHECK_TWOPAIRS - END");

print("CHECK_JACKORBETTER - START");
for (new _c=0; _c<5; _c++) {
new _c = cPokerGame[playerid][_c][1]; //My error was here, I re-defined _c
if (_c >= CARD_JACK) {
return CHECK_JACKORBETTER;
}
}


Turned out I was redefining the loop variable, inside the loop. But whats strange, is



print("CHECK_TWOPAIRS - END");

print("CHECK_JACKORBETTER - START");



was completely skipped in the output, so i thought the error was between "CHECK_TWOPAIRS - START" and "CHECK_TWOPAIRS - END"

thanks for the help though :D