Posted: 15th Aug 2022 15:18
I've managed writing a single integer to file fine but is there a way to write more than one to the same file or is it necessary to
start again with calls to OpenToWrite, WriteInteger, CloseFile? An example would be most appreciated; as would an example of it's complementary Read functions. Please and thank you
Posted: 15th Aug 2022 15:24
As far as I remember, when I myself used this command, you have to start recording from the very beginning.
So you can't go wrong.
and do not close the file until you write everything.
Posted: 15th Aug 2022 16:44
one way using CSV (comma-separated values) to build a string of 10 integers into a single line of data:
+ Code Snippet
// Project: Data 
// Created: 2022-08-15
// By: Virtual Nomad
// show all errors
SetErrorMode(2)

// set window properties
SetWindowTitle( "Data" )
SetWindowSize( 1280,720, 0 )
SetWindowAllowResize( 1 )

// set display properties
SetVirtualResolution( 1280,720)
SetOrientationAllowed( 1, 1, 1, 1 )
SetSyncRate( 30, 0 ) 
SetScissor( 0,0,0,0 )
UseNewDefaultFonts( 1 ) 

GLOBAL Data as Integer [9,9]
GenerateData()
SaveData()

GenBUT = 1	:	AddVirtualButton(GenBUT,1000,50,100)	:	SetVirtualButtonText(GenBUT,"GENERATE")
SaveBUT = 2	:	AddVirtualButton(SaveBUT,1000,150,100)	:	SetVirtualButtonText(SaveBUT,"SAVE")
LoadBUT = 3	:	AddVirtualButton(LoadBUT,1000,250,100)	:	SetVirtualButtonText(LoadBUT,"LOAD")
OpenBUT = 4	:	AddVirtualButton(OpenBUT,1000,350,100)	:	SetVirtualButtonText(OpenBUT,"OPEN")

do

    If GetRawKeyState(27) then End    

	If GetVirtualButtonPressed(GenBUT) then GenerateData()
	If GetVirtualButtonPressed(SaveBUT) then SaveData()
	If GetVirtualButtonPressed(LoadBUT) then LoadData()
	If GetVirtualButtonPressed(OpenBUT) then OpenFile()

	ShowData()

    Sync()
loop

Function GenerateData() //fill 10x10 array with random integers
	for y = 0 to 9
		for x = 0 to 9
			Data[x,y] = Random(0,1000)
		next x
	next y
EndFunction

Function SaveData() //save 1 row at a time with each # separated by a comma
	ThisFile = OpenToWrite("data.dat")
	for y = 0 to 9
		ThisRow$ = ""
		for x = 0 to 9
			If x = 0
				ThisRow$ = STR(Data[x,y])
			Else
				ThisRow$ = ThisRow$ + "," + STR(Data[x,y])
			EndIf
		next x
		WriteLine(ThisFile,ThisRow$)
	next y
	CloseFile(ThisFile)
EndFunction

Function ShowData() //assemble each array row as a single string for print display
	for y = 0 to 9
		ThisRow$ = ""
		for x = 0 to 9
			If x = 0
				ThisRow$ = STR(Data[x,y])
			Else
				ThisRow$ = ThisRow$ + "," + STR(Data[x,y])
			EndIf
		next x
		Print(ThisRow$)
	next y
EndFunction

Function LoadData() //read each row and assign integers separated by commas to appropriate data index
	ThisFile = OpenToRead("data.dat")
	for y = 0 to 9
		ThisRow$ = ReadLine(ThisFile)
		for x = 1 to CountStringTokens(ThisRow$,",") //could be 1-10 since we know we wrote 10 integers
			Data[x-1,y] = VAL (GetStringToken(ThisRow$,",",x) ) //x-1 since array starts at 0
		next x
	next y
	CloseFile(ThisFile)
EndFunction

Function OpenFile() //file was saved to write path
	OpenBrowser(GetWritePath()+"/media/data.dat")
EndFunction

no idea what you're doing with the integers so i'm just feeding the data into a 10x10 array for demonstration purposes (extracting single values from each string):

have a play with it.

add: i just re-read the question and it seems you were opening a file, writing an integer, closing the file for every value that you wanted to write. with the code provided, it's obviously not required. just Open File, Write/Read everything, Close File.

then, again, i mis-read the question. if you want a single integer on each line, i could modify the code. just ask and sorry for assuming (and not having consumed enough coffee before going on this adventure)
Posted: 15th Aug 2022 17:17
You can write any number of integers to a file in one go. Here is an example which does the following:
- Opens a file to write (will overwrite an existing file if it exists).
- Write 50 integers, all held in an array called "stats".
- Close the file.
+ Code Snippet
	statfile = OpenToWrite("mystatsfile.dat")
	for s=1 to 50
		WriteInteger(statfile, stats[s])
	next s
	CloseFile(statfile)
Posted: 15th Aug 2022 17:25
@zappo, is it just me or is WriteInteger() adding an "empty" line to the file?

+ Code Snippet
// Project: ReadWriteIntegers 
// Created: 2022-08-15
// By: Virtual Nomad
// show all errors
SetErrorMode(2)

// set window properties
SetWindowTitle( "ReadWriteIntegers" )
SetWindowSize( 1280,720, 0 )
SetWindowAllowResize( 1 )

// set display properties
SetVirtualResolution( 1280,720)
SetOrientationAllowed( 1, 1, 1, 1 )
SetSyncRate( 30, 0 ) 
SetScissor( 0,0,0,0 )
UseNewDefaultFonts( 1 ) 

GLOBAL Data as Integer []
GenerateIntegers()
LoadIntegers()

OpenBUT = 1	:	AddVirtualButton(OpenBUT,1000,100,100)	:	SetVirtualButtonText(OpenBUT,"OPEN")

do
    If GetRawKeyState(27) then End    

	ShowIntegers()
	If GetVirtualButtonPressed(OpenBUT) then OpenBrowser(GetWritePath()+"media/data.dat")
    Sync()
loop

Function GenerateIntegers()
	TotalIntegers = Random(5,15) //write a random # of random integers
	ThisFile = OpenToWrite("data.dat")
		For x = 1 to TotalIntegers
			WriteInteger(ThisFile, Random(10,1000) )
		Next x
	CloseFile(ThisFile)
EndFunction

Function LoadIntegers()
	ThisFile = OpenToRead("data.dat")
	Repeat
		Data.Insert(ReadInteger(ThisFile))
	Until FileEOF(ThisFile)
	CloseFile(ThisFile)
EndFunction

Function ShowIntegers()
	For x = 0 to Data.Length
		Print( STR(Data[x]) )
	Next x
EndFunction


i think i've experienced this before and it seems like a bug unless i'm doing something wrong?
Posted: 15th Aug 2022 18:09
Thanks to all! Each of your answers provided useful insight. Lightning fast responses and robust detailed answers are why the agk forum is mvp
Posted: 15th Aug 2022 18:22
ur welcome, zandy.

i do tend to learn something myself when i partake in these exercises so, it's a win-win (-win-win-win...) for all of us

always forward!
Posted: 15th Aug 2022 21:51
@Virtual Nomad: You should check FileEOF immediately after Reading before adding to Data.
Posted: 16th Aug 2022 17:40
so:
+ Code Snippet
Function LoadIntegers()
	ThisFile = OpenToRead("data.dat")
	Do
		ThisINT = ReadInteger(ThisFile)
		If FileEOF(ThisFile)
			Exit
		Else
			Data.Insert(ThisINT)
		EndIf
	Loop
	CloseFile(ThisFile)
EndFunction

...to read an unknown number of integers/lines/etc.

i can't believe i didn't know this since i don't think i've had issues when reading files as i've always done... i figured EOF had an ascii value like EOL where that last EOL would be replaced by (an ascii) EOF at the end of the last line in a given file somehow (via CloseFile()).

i've since read a little on EOF and think i understand why it doesn't work that way.

thanks for the lesson
Posted: 23rd Aug 2022 15:35
Instead of using DO:LOOP and relying on EXIT, use a control loop that's designed for exiting on a condition. WHILE is probably the better choice over REPEAT unless you can guarantee the file will always have at least something to read first. WHILE would protect you from empty files.


While:
+ Code Snippet
ThisFile = OpenToRead("data.dat")
while(not FileEOF(ThisFile))
	ThisINT = ReadInteger(ThisFile)
	Data.Insert(ThisINT)
endwhile
CloseFile(ThisFile)



Repeat:
+ Code Snippet
ThisFile = OpenToRead("data.dat")
repeat
	ThisINT = ReadInteger(ThisFile)
	Data.Insert(ThisINT)
until(FileEOF(ThisFile))
CloseFile(ThisFile)
Posted: 23rd Aug 2022 18:45
@Phaelax: FileEOF should be checked immediately after attempting a read command. Both code snippets you posted will add an extra, non-existent 0 to the end of Data.

We don't have a way to do loops like this:
+ Code Snippet
while ((c = getchar()) != EOF) {}