Author Topic: Problem with OPEN in SUB  (Read 1342 times)

0 Members and 1 Guest are viewing this topic.

Offline RobinGravel

  • Newbie
  • Posts: 30
Problem with OPEN in SUB
« on: February 25, 2022, 09:58:32 pm »
I'm making a game and I need SUBs instead using GOSUBs.

Code: QB64: [Select]
  1. TYPE testing
  2.  t1 AS STRING * 12
  3.  t2 AS STRING * 12
  4.  t3 AS STRING * 12
  5. DIM ttt AS testing
  6. DECLARE SUB text (g, tt, testing, t1, t2, t3)
  7. text 1, tt, testing, t1, t2, t3
  8.  
  9. SUB text (g, ttt, testing, t1, t2, t3)
  10. OPEN "test.txt" FOR RANDOM AS 1 LEN = 36
  11. max = LOF(1) / LEN(ttt)
  12. GET #1, g, ttt
  13. PRINT ttt.t1
  14. PRINT ttt.t2
  15. PRINT ttt.t3
  16. k$ = INPUT$(1): CLOSE
  17.  

No message error but it doesn't give the right results.


Without SUB, the program works as intended.

Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5.  
  6. Dim ttt As testing: Cls
  7. Open "test.txt" For Random As 1 Len = 36
  8. max = LOF(1) / Len(ttt)
  9. For z = 1 To 2
  10.     Get #1, z, ttt
  11.     Print ttt.t1
  12.     Print ttt.t2
  13.     Print ttt.t3
  14.     Print
  15. k$ = Input$(1): Close
  16.  

Here the code to create TEST.TXT

Code: QB64: [Select]
  1. 'Ftexte
  2.  
  3. TYPE testing
  4.    t1 AS STRING * 12
  5.    t2 AS STRING * 12
  6.    t3 AS STRING * 12
  7.  
  8. DIM ttt AS testing
  9. K$ = INPUT$(1)
  10. '
  11.  OPEN "test.txt" FOR RANDOM AS 1 LEN = LEN(ttt): limit = LEN(ttt)
  12.  FOR z = 1 TO 2
  13.  READ m1$, m2$, m3$
  14.  ttt.t1 = m1$: ttt.t2 = m2$: ttt.t3 = m3$
  15.  PUT #1, z, ttt
  16.  NEXT z
  17.  CLS : PRINT "Saved": K$ = INPUT$(1)
  18. '
  19.  
  20. DATA "123456789012"
  21. DATA "Hello World!"
  22. DATA " Good day.  "
  23.  
  24. DATA "ABCDEFGHIJKL"
  25. DATA "Chichen.    "
  26. DATA "Pizza  Hotel"
  27.  

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: Problem with OPEN in SUB
« Reply #1 on: February 25, 2022, 10:31:18 pm »
Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5. Dim ttt As testing
  6.  
  7. GetRec 1, ttt
  8. Print ttt.t1
  9. Print ttt.t2
  10. Print ttt.t3
  11.  
  12. Sub GetRec (recNum As Long, ttt As testing)
  13.     lenRec% = Len(ttt) ' <<<<<<<<<<<<< I had to do this to get the crazy thing to work
  14.     Open "test.txt" For Random As #1 Len = lenRec%
  15.     Get #1, recNum, ttt
  16.     Close
  17.  
  18.  
  19.  

I cut to the chase.

An alternate way to show you don't need to match ttt in the sub definition:
Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5. Dim rec As testing
  6.  
  7. GetRec 1, rec
  8. Print rec.t1
  9. Print rec.t2
  10. Print rec.t3
  11.  
  12. Sub GetRec (recNum As Long, ttt As testing)
  13.     lenRec% = Len(ttt) ' <<<<<<<<<<<<< I had to do this to get the crazy thing to work
  14.     Open "test.txt" For Random As #1 Len = lenRec%
  15.     Get #1, recNum, ttt
  16.     Close
  17.  

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: Problem with OPEN in SUB
« Reply #2 on: February 26, 2022, 12:25:51 am »
Oh sure! Now it works as I thought I tried originally. The secret is to save the file before Running I bet.
Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5. Dim rec As testing
  6.  
  7. GetRec 1, rec
  8. Print rec.t1
  9. Print rec.t2
  10. Print rec.t3
  11.  
  12. Sub GetRec (recNum As Long, ttt As testing)
  13.     'lenRec% = Len(ttt) ' >>> commented out <<<<<<<<<<<<< I had to do this to get the crazy thing to work
  14.     Open "test.txt" For Random As #1 Len = Len(ttt)
  15.     Get #1, recNum, ttt
  16.     Close
  17.  

Offline SMcNeill

  • QB64 Developer
  • Forum Resident
  • Posts: 3972
    • Steve’s QB64 Archive Forum
Re: Problem with OPEN in SUB
« Reply #3 on: February 26, 2022, 12:28:48 am »
You should toss an error check in the @bplus.

If record num < 1 OR record num > file length \ record length THEN ERROR!  Out of bounds record.
https://github.com/SteveMcNeill/Steve64 — A github collection of all things Steve!

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: Problem with OPEN in SUB
« Reply #4 on: February 26, 2022, 12:33:25 am »
Yeah e had this in sub originally which was a start of one, I think:
Code: QB64: [Select]
  1. max = LOF(1) / Len(ttt)
  2.  

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: Problem with OPEN in SUB
« Reply #5 on: February 26, 2022, 06:33:38 am »
Here's a proper write up then
Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5. Dim rec As testing
  6.  
  7. GetRec 0, rec ' try this with 1 should get record, at 10 or 0 should see error message.
  8. Print rec.t1
  9. Print rec.t2
  10. Print rec.t3
  11.  
  12. Sub GetRec (recNum As Long, ttt As testing)
  13.     Dim As Long max
  14.     Open "test.txt" For Random As #1 Len = Len(ttt)
  15.     max = LOF(1) \ Len(ttt)
  16.     If recNum > 0 And recNum <= max Then
  17.         Get #1, recNum, ttt
  18.     Else
  19.         Print "Error, recNum is too high or 0."
  20.     End If
  21.     Close
  22.  

Offline RobinGravel

  • Newbie
  • Posts: 30
Re: Problem with OPEN in SUB
« Reply #6 on: February 26, 2022, 11:06:59 am »
I manage to make PRINTs to work inside the SUB. So I don't need to overuse PRINT all the time.

Code: QB64: [Select]
  1. Type testing
  2.     t1 As String * 12
  3.     t2 As String * 12
  4.     t3 As String * 12
  5. Dim rec As testing
  6.  
  7. GetRec 1, rec: GetRec 2, rec
  8. k$ = Input$(1)
  9. Sub GetRec (recNum, rec As testing)
  10.     'Dim As Long max
  11.     Open "test.txt" For Random As #1 Len = Len(rec)
  12.     max = LOF(1) / Len(rec)
  13.     If recNum > 0 And recNum <= max Then
  14.         Get #1, recNum, rec
  15.     Else
  16.         Print "Error, recNum is too high or 0.": End
  17.     End If
  18.     Close
  19.     Print rec.t1: Print rec.t2: Print rec.t3: Print
  20.  

Thanks for help.
« Last Edit: February 26, 2022, 11:13:48 am by RobinGravel »

Offline Pete

  • Forum Resident
  • Posts: 2361
  • Cuz I sez so, varmint!
Re: Problem with OPEN in SUB
« Reply #7 on: February 26, 2022, 11:33:34 am »
In these last two examples, it doesn't matter where the PRINT statements are at all. You can have them in the sub or in the main, but my point is it's just a coding style choice. Subs are just ways to better organize program flow and allow for a single routine to be used instead or coding repeated routines in a main. I saw your initial post contained a FOR/NEXT loop. If you need to call both the sub with a print routine or the sub with the print routine n the main, yuo would simply include that call in the FOR/NEXT loop..

Code: QB64: [Select]
  1. FOR pete = 1 TO 2
  2.     CALL mysubroutine(a$)
  3. NEXT pete
  4.  
  5. SUB mysubroutine (a$)
  6.     a = a + 1
  7.     PRINT "Next Pete? You mean another one is out there? :O"

or...

Code: QB64: [Select]
  1. FOR pete = 1 TO 2
  2.     CALL mysubroutine(a$)
  3.     PRINT "Next Pete? You mean another one is out there? :O"
  4. NEXT pete
  5.  
  6. SUB mysubroutine (a$)
  7.     a = a + 1

My coding style preference would also be to place the print statement in the sub, but again, that's just a preference. There is no "overuse" that i see, in either of the two examples above.

Happy coding!

Pete
Want to learn how to write code on cave walls? https://www.tapatalk.com/groups/qbasic/qbasic-f1/

Offline Cobalt

  • QB64 Developer
  • Forum Resident
  • Posts: 878
  • At 60 I become highly radioactive!
Re: Problem with OPEN in SUB
« Reply #8 on: February 26, 2022, 12:22:01 pm »
Would have been nice if somebody would have pointed out what you did wrong, though you might of garnered it from the example replies.

This was your original issue;

SUB text (g, ttt, testing, t1, t2, t3)

If you wanted to pass a UDT you needed to use the AS statement just like in a DIM line

SUB text (g, ttt AS testing)
called with
text 1, ttt

in your original line, each of those variables being passed were passed as the SINGLE data type, by default since you did not specify.

That is why you were not seeing the results you expected.

Now you didn't receive any kind of error because you didn't write one bit of code wrong! Every thing you typed was valid code. Just not the code that would produce the results you wanted.  ttt.t1 is a valid variable even without UDT.

and GET #1, g, ttt
worked correctly too it loaded 4bytes (length of a SINGLE) into ttt, but instead of as a STRING it loaded it as a SINGLE(numeric) value. so no error

and of course PRINT ttt.t1 would have printed 0 as ttt.t1 was a SINGLE value that had nothing assigned to it.(same with the other 2 print lines) so still no error

max = LOF(1) / LEN(ttt)
here LEN(ttt) would have been 4, again because ttt is a SINGLE value which is 4 bytes long. again no error on the compiler side.

Hopefully that explains what occurred, and you can avoid (or make) some problems in the future with this knowledge.
Granted after becoming radioactive I only have a half-life!

Offline Pete

  • Forum Resident
  • Posts: 2361
  • Cuz I sez so, varmint!
Re: Problem with OPEN in SUB
« Reply #9 on: February 26, 2022, 01:00:09 pm »
@Cobalt makes a good point.

Personally I find the use of UDT's useful for large apps with many parameter to pass to many subs. It saves a ton of typing and dramatically reduces line sizes. For smaller apps or non-sub snippets, I tend not to use them. I suppose some people, in either case, may prefer UDT's for better variable naming, especially grouping of variable names to assignments.

Pete
Want to learn how to write code on cave walls? https://www.tapatalk.com/groups/qbasic/qbasic-f1/

Offline RobinGravel

  • Newbie
  • Posts: 30
Re: Problem with OPEN in SUB
« Reply #10 on: February 26, 2022, 01:07:15 pm »
Would have been nice if somebody would have pointed out what you did wrong, though you might of garnered it from the example replies.

This was your original issue;

SUB text (g, ttt, testing, t1, t2, t3)

If you wanted to pass a UDT you needed to use the AS statement just like in a DIM line

SUB text (g, ttt AS testing)
called with
text 1, ttt

in your original line, each of those variables being passed were passed as the SINGLE data type, by default since you did not specify.

That is why you were not seeing the results you expected.

Now you didn't receive any kind of error because you didn't write one bit of code wrong! Every thing you typed was valid code. Just not the code that would produce the results you wanted.  ttt.t1 is a valid variable even without UDT.

and GET #1, g, ttt
worked correctly too it loaded 4bytes (length of a SINGLE) into ttt, but instead of as a STRING it loaded it as a SINGLE(numeric) value. so no error

and of course PRINT ttt.t1 would have printed 0 as ttt.t1 was a SINGLE value that had nothing assigned to it.(same with the other 2 print lines) so still no error

max = LOF(1) / LEN(ttt)
here LEN(ttt) would have been 4, again because ttt is a SINGLE value which is 4 bytes long. again no error on the compiler side.

Hopefully that explains what occurred, and you can avoid (or make) some problems in the future with this knowledge.

Understood.