fixed: Generator: when making [if-index]

[if-index] statement has to look for a last [for] statement on the stack
       (because the stack is for all items now)


git-svn-id: svn://ttmath.org/publicrep/ezc/trunk@394 e52654a7-88a9-db11-a3e9-0013d4bc506e
This commit is contained in:
Tomasz Sowa 2012-03-03 20:58:55 +00:00
parent 787b5e99b2
commit 68c1fb8ef8
2 changed files with 30 additions and 8 deletions

View File

@ -74,12 +74,16 @@ struct FunData
this object would be immediately removed) this object would be immediately removed)
remove - when true it means that object pointing by fun_data should be automatically remove - when true it means that object pointing by fun_data should be automatically
removed -- (by using delete fun_data) removed -- (by using delete fun_data)
is_for - true if the item is from [for] statement
currently used only in [if-index]
(it has to look for the last [for] item)
*/ */
struct Stack struct Stack
{ {
size_t iter; size_t iter;
FunData * fun_data; FunData * fun_data;
bool remove; bool remove;
bool is_for;
Stack() Stack()
{ {
@ -91,6 +95,7 @@ struct Stack
iter = 0; iter = 0;
fun_data = 0; fun_data = 0;
remove = true; remove = true;
is_for = false;
} }
}; };

View File

@ -189,6 +189,7 @@ private:
void TrimWhite(const wchar_t *& start, const wchar_t *& end); void TrimWhite(const wchar_t *& start, const wchar_t *& end);
void SkipWhite(const wchar_t *& str); void SkipWhite(const wchar_t *& str);
size_t StrToSize(const wchar_t * str, const wchar_t ** str_end); size_t StrToSize(const wchar_t * str, const wchar_t ** str_end);
bool LookForLastForStatement(size_t & last_for_index);
void CreateMsg(StreamType & out, const wchar_t * type, const wchar_t * arg = 0); void CreateMsg(StreamType & out, const wchar_t * type, const wchar_t * arg = 0);
void CreateMsg(const wchar_t * type, const wchar_t * arg = 0); void CreateMsg(const wchar_t * type, const wchar_t * arg = 0);
@ -198,7 +199,7 @@ private:
bool LimitAchieved(); bool LimitAchieved();
void MakeTextIf_go(Item & item, bool result); void MakeTextIf_go(Item & item, bool result);
bool MakeTextIfindexnumber(Item & item, bool & result); bool MakeTextIfindexnumber(Item & item, size_t for_index, bool & result);
void MakeTextIf(Item & item); void MakeTextIf(Item & item);
void MakeTextIfno(Item & item); void MakeTextIfno(Item & item);
void MakeTextIfany(Item & item); void MakeTextIfany(Item & item);
@ -1064,12 +1065,24 @@ void Generator<StreamType>::MakeTextIsno(Item & item)
template<class StreamType>
bool Generator<StreamType>::LookForLastForStatement(size_t & last_for_index)
{
last_for_index = stack_index;
while( last_for_index-- > 0 )
{
if( stack_tab[last_for_index].is_for )
return true;
}
return false;
}
template<class StreamType> template<class StreamType>
bool Generator<StreamType>::MakeTextIfindexnumber(Item & item, bool & result) bool Generator<StreamType>::MakeTextIfindexnumber(Item & item, size_t for_index, bool & result)
{ {
if( item.functions.size() != 1 ) if( item.functions.size() != 1 )
return false; return false;
@ -1085,7 +1098,7 @@ bool Generator<StreamType>::MakeTextIfindexnumber(Item & item, bool & result)
return false; return false;
} }
result = (stack_tab[stack_index-1].iter == number); result = (stack_tab[for_index].iter == number);
return true; return true;
} }
@ -1095,28 +1108,30 @@ return true;
template<class StreamType> template<class StreamType>
void Generator<StreamType>::MakeTextIfindex(Item & item) void Generator<StreamType>::MakeTextIfindex(Item & item)
{ {
if( item.functions.size() != 1 ) size_t for_index;
if( item.functions.size() != 1 || !LookForLastForStatement(for_index) )
return; return;
bool result = false; bool result = false;
if( item.functions[0].name == L"odd" ) if( item.functions[0].name == L"odd" )
{ {
result = (stack_tab[stack_index-1].iter & 1) == 1; result = (stack_tab[for_index].iter & 1) == 1;
} }
else else
if( item.functions[0].name == L"even" ) if( item.functions[0].name == L"even" )
{ {
result = (stack_tab[stack_index-1].iter & 1) == 0; result = (stack_tab[for_index].iter & 1) == 0;
} }
else else
if( item.functions[0].name == L"first" ) if( item.functions[0].name == L"first" )
{ {
result = stack_tab[stack_index-1].iter == 0; result = stack_tab[for_index].iter == 0;
} }
else else
{ {
if( !MakeTextIfindexnumber(item, result) ) if( !MakeTextIfindexnumber(item, for_index, result) )
return; return;
} }
@ -1128,6 +1143,8 @@ void Generator<StreamType>::MakeTextIfindex(Item & item)
template<class StreamType> template<class StreamType>
void Generator<StreamType>::MakeTextForLoop(Item & item, typename Functions<StreamType>::Function * function) void Generator<StreamType>::MakeTextForLoop(Item & item, typename Functions<StreamType>::Function * function)
{ {
stack_tab[stack_index-1].is_for = true;
for( ; !break_generating ; stack_tab[stack_index-1].iter += 1 ) for( ; !break_generating ; stack_tab[stack_index-1].iter += 1 )
{ {
if( stack_tab[stack_index-1].iter >= max_for_items ) if( stack_tab[stack_index-1].iter >= max_for_items )