B4R Question For-Next error after 16 cycle in JoinStrings

petr4ppc

Well-Known Member
Licensed User
Longtime User
Dear friend please for advice:

I have code:
B4X:
Dim buffer() As Byte = "hallo how are xyz I am fine and you?"
For i = 0 To buffer.Length-1
Dim cbtx(1) As Byte
byteconvert.ArrayCopy2(buffer,i,cbtx,0,1)
receivebyte = byteconvert.StringFromBytes(cbtx)
allbytesasstringarehere= JoinStrings(Array As String(allbytesasstringarehere, receivebyte)) 
next

But I get this error after i=16 ("z") in word "xyz"


Please what can I do?
Everytime only 16 cycles of FOR-NEXT is processed and then I get this error.
Thank you
p4ppc
 

emexes

Expert
Licensed User
Because you are dealing more with bytes one-by-one than with strings, you might need be making single-byte arrays like:
B4X:
Queue.AddBytesToLast(Array As Byte(64 + 8))     'H'
Queue.AddBytesToLast(Array As Byte(96 + 1))     'a'
Queue.AddBytesToLast(Array As Byte(96 + 12))    'l'
Queue.AddBytesToLast(Array As Byte(96 + 12))    'l'
Queue.AddBytesToLast(Array As Byte(96 + 15))    'o'
Queue.AddBytesToLast(Array As Byte(33))         '!'

Dim bc As ByteConverter
Dim JoinedString As String = bc.StringFromBytes(Queue.FirstItem())    'might not need the ()
 
Upvote 0

petr4ppc

Well-Known Member
Licensed User
Longtime User
EMEXES,

thank you for your tip...
I am learning...And I think, that
B4X:
RemoveFirst
helps to secure only small memory consumption...(i dont know it for certain)

But if I have true (if I understand Erels Idea), then I think, that solution can be
0) receive serial data (for example "Hallo1234xouer1258"
1) use Queue mechanism for reading each received byte - byte by byte (because of small memory)
2) collect some of this bytes to new BYTE array, for example "Hallo"
3) then convert this byte array to string "Hallo"
4) send this string via standard serial back, for example "Hallo"

Best regards
p4ppc
 
Upvote 0

emexes

Expert
Licensed User
I am learning...
Warms my heart

And I think, that
B4X:
RemoveFirst
helps to secure only small memory consumption...
What it does is remove the item (in your case, the byte) that is to next come off/out the queue. One byte, not the whole string (unless you've converted to using .AddBytesToLast). You would only call .RemoveFirst after you have processed .FirstItem().

that solution can be
B4X:
'0) receive serial data (for example "Hallo1234xouer1258"
Queue.AddBytesToLast("Hallo")
Queue.AddBytesToLast("123")
Queue.AddBytesToLast("4xouer12")
Queue.AddBytesToLast("58")

'... OR SOMETHING LIKE THIS ...

'1) use Queue mechanism for reading each received byte - byte by byte (because of small memory)
'2) collect some of this bytes to new BYTE array, for example "Hallo"
Do While SerialByteReady()
    Dim ReceivedByte As Byte = SerialGetNextByte()
    If ReceivedByte = 0x0A or ReceivedByte = 0x0D Then    'if end-of-line / end-of-packet marker
        HandlePacket( Queue.FirstItem() )    'might not need ()
        Queue.RemoveFirst    'clear packet buffer ready for next packet
    Else
        Queue.AddBytesToLast(Array As Byte(ReceivedByte))    'add received byte to packet buffer
    End If
Loop

'3) then convert this byte array to string "Hallo"
Dim WholeString as String = Queue.FirstItem()    'might not need ()
Dim PartialString As String = WholeString.Substring2(0, 5)    'returns only first 5 characters eg "Hallo"
Queue.RemoveFirst    'clears queue (which only contains one item) in preparation for receiving next string

'4) send this string via standard serial back, for example "Hallo"
Serial.PutString( PartialString )    'or whatever your serial library transmit routine is called
Again, I can't easily test this here, but... hopefully the gist of it is enough to get you closer to the finish line
 
Upvote 0

petr4ppc

Well-Known Member
Licensed User
Longtime User
Dear friends,

EMEXES - thank you very much for your help and advices
EREL - thank you very much for your help and advices

EMEXES:
is good to see you're fully on-board with concept of zero-based indexing
I am by Anywhere logicaly rebuilded after this weekend (I was alone) I spoke tommorow with my girl in BIT declaration - YES, NO. And I was surprised - She is happy - I think that she is happy because she know what I did at the weekend

Please
Log("Output:",Queue.FirstItem)
this write "hallo"
but here:
B4X:
Dim WholeString As String = byteconvert.StringFromBytes(Queue.FirstItem) 'FirstItem()    'might not need ()
Dim WholeString2 As String = Queue.FirstItem
        Log("WHOLE-",WholeString)
        Log("WHOLE2-",WholeString2)

I am doing some mistake I cant put Queue.FirstItem to string...

EREL - I will try to print serial byte to byte...thank you

EDIT
Excuse me - my mistake, I had Queue.REMOVEFIRST before code:
B4X:
Dim WholeString As String = byteconvert.StringFromBytes(Queue.FirstItem)
This functioned and I ger now string in:
B4X:
Log("WHOLE-",WholeString)

I go work with Emexes code and I will write result.
Thank you very much
Best regards
p4ppc
 
Last edited:
Upvote 0

emexes

Expert
Licensed User
I am by Anywhere logicaly rebuilded after this weekend (I was alone) I spoke tommorow with my girl in BIT declaration - YES, NO. And I was surprised - She is happy - I think that she is happy because she know what I did at the weekend
I feel there is humour buried in there somewhere, but it has lost something in translation. Or perhaps gained something?!?!

I'll be back in ten minutes to process the rest of the post.

 
Upvote 0

petr4ppc

Well-Known Member
Licensed User
Longtime User
EMEXES - yes I have tried humour. I only explained, that my girl recognized after she came back home (after 3 days) that - everything was OK, I was good at the weekend. And why?
Because after three days talking with my computer I can communicate with her only in BIT resolution = I can say to her only YES or NOT. And in this situation she like this resolution. Because she knows that I was not outside my flat - that I was not in some club or somethig else...I sit with my PC. I must explain - She is talking with me in very long STRING resolution.

What is interresting on this?

1-Interresting is that in situation, when she come back home after few days and my communication with her is in BIT resolution - then it is OK for her. (she recognize that I was not in the club)
0-But when she is home with me long time and I am starting talking with her in BIT resolution = only YES or NOT then it is for her NOT OK.

And result?
I must find the way how to convert her speak from strings to bit.
 
Last edited:
Upvote 0

emexes

Expert
Licensed User
Why do you need to 'join' anything? Call AStream.Write multiple times instead.
I go work with Emexes code
Petr (?)

I am with Erel, regarding that it is difficult to give good advice, without having actual real data to work with.

The packets that you are receiving via the serial port:

- are they ASCII or binary format
- fixed or variable length?
- delimited, or with a length specifier?
- any fixed known bytes at the beginning and/or end of the packet?
- checksum?

and ditto re: the packets you are transmitting via serial port.

and I will write result.

I am hanging out for this!
 
Upvote 0

petr4ppc

Well-Known Member
Licensed User
Longtime User
Dear EMEXES

it is SOLVED

I absolutely agree with you and I understand. I think that you and Erel gives to me everything what I need for finding solution.
I am humble and grateful, I appreciate yours advices.

Here I am sending final solution which is perfect for me because of memory. This solution take only small fragment of memory (STACK=+-200) than JoinString (STACK=+-2000). (In my case)

B4X:
                For repeat=3 To Buffer.Length-1
                                             
                           Dim cbt(1) As Byte
                           byteconvert.ArrayCopy2(Buffer,repeat,cbt,0,1)
                           letter= byteconvert.StringFromBytes(cbt)
                                             
                           If letter=")" Then 'process
                                        Queue.AddBytesToLastItem(")")
                                        Dim thisisresult As String = byteconvert.StringFromBytes(Queue.FirstItem)
                                        Do While Queue.Size > 0
                                            Queue.RemoveFirst
                                        Loop

                            End If
                            If letter<>"(" And letter<>")" and letter...and letter...and letter....     Then Queue.AddBytesToLastItem(letter)                                             
Next

                 Log("WHOLE-",thisisresult)
                '  Now I can work with result and this FOR-NEXT cycle take minimal STACk memory *** its PERFECT!! This I need

Thank you very much,
BEST REGARDS
p4ppc
 
Upvote 0
Cookies are required to use this site. You must accept them to continue using the site. Learn more…