Wednesday, November 20, 2019

#1 2019-10-13 07:15:24 am

scrutinizer82
Member
Registered: 2015-08-04
Posts: 15

Trying to read as list raises «error of type -116»

The script in question is below. It concatenates sublists to leave only the parent list so that items of the previous sublists would populate the parent list only.

I need to see the result upon completion of each loop and the result is of the class "list" stored in the varible

items_to_process

The script successfully writes the contents of the variable as list but fails to read it back similarly as list. Instead, the OS returns a very strange "error of type -116". I already learned that this error means memory depletion (as per this description at http://www.cs.cmu.edu/afs/cs/user/lenzo … rrors.html) however that doesn't solve the reason for this error to occur, in the first place. Would you point me to a mistake I made?

Applescript:

set items_to_process to {{}, {"Affinity Designer", "Affinity Photo", {}, {}, {}}, {}, {}, {}}

JoinListItems(items_to_process)
set theFile to (((path to desktop) as text) & "Concatenated-log") as alias

read theFile as list



on JoinListItems(items_to_process)
   set Concatenated to {}
   set IsJoined to false
   repeat until IsJoined
       set IsJoined to true
       repeat ((count items_to_process) - 1) times
           
           set Concatenated to (item 1 of items_to_process & item 2 of items_to_process)
           if (count items_to_process) = 2 then
               
               set items_to_process to Concatenated
               exit repeat
           end if
           set items_to_process to {Concatenated} & ((items 2 thru -1) of (rest of items_to_process))
           set theFilePath to (((path to desktop) as text) & "Concatenated-log")
           set LogFile to open for access file theFilePath with write permission
           set ThePosition to get eof file theFilePath
           write items_to_process to LogFile as list starting at ThePosition
           close access LogFile
       end repeat
       
       
       
       repeat with anItem in items_to_process
           if class of contents of anItem is list then
               set IsJoined to false
               my JoinListItems(items_to_process)
               
           end if
       end repeat
   end repeat
   return items_to_process
end JoinListItems

Model: MacBook Pro
AppleScript: 2.3.2
Browser: Safari 9537.86.7
Operating System: macOS 10.9


Currently running Mac OS X 10.7.5, OS X 10.9.5, macOS 10.13.6

Interests: AppleScript, Automator, Unix


Filed under: write, Read, access, error -116

Offline

 

#2 2019-10-13 08:22:34 am

Nigel Garvey
Moderator
From:: Warwickshire, England
Registered: 2002-11-20
Posts: 5105

Re: Trying to read as list raises «error of type -116»

Hi.

What result are you trying to achieve? You're repeatedly and recursively writing lists to the end of the file, overwriting the last byte in the file each time. That seems to be what's causing the 'read' failure. The 'write' line should be:

Applescript:

write items_to_process to LogFile as list starting at eof

'eof' is the insertion point at the end of the file. When you use 'get eof', you effectively get the index of the last byte in the file, so writing from there overwrites that byte. 'starting at eof' ensures that writing begins after the last byte.

That said, the 'read' command only seems to read to the end of the first list it encounters, so even when the 'write' command's corrected, only the first list written is read back — unless (presumably) you know at which byte each subsequent list begins and can specify the read to start from there.

You don't have any error trapping to close the file in the event of the script crashing while it's open!


NG

Offline

 

#3 2019-10-13 10:55:58 am

scrutinizer82
Member
Registered: 2015-08-04
Posts: 15

Re: Trying to read as list raises «error of type -116»

You don't have any error trapping to close the file in the event of the script crashing while it's open!


That's because I'm dealing with at least a known error and know how to trap it so I made this sacrifice intentionally.

'eof' is the insertion point at the end of the file. When you use 'get eof', you effectively get the index of the last byte in the file, so writing from there overwrites that byte. 'starting at eof' ensures that writing begins after the last byte.



That was quite a revelation and I never read about these nuances. I presumed that get eof implies the end position as well and nowhere did I come across the notion of (get eof) meaning something other than the end of a file. In fact, I can hardly grasp the difference between the end of a file and the index of the last byte of the file: don't they pertain to the same thing?

You're repeatedly and recursively writing lists to the end of the file, overwriting the last byte in the file each time.

which is unexpected because what I wanted was to append the list variable containing the value as it appears at the end of each loop cycle to the same file (Concotenated-log). I want to get the following:

{items after the 1st cycle}
{items after the 2nd cycle}
...
{items after the last cycle}.

Currently running Mac OS X 10.7.5, OS X 10.9.5, macOS 10.13.6

Interests: AppleScript, Automator, Unix

Offline

 

#4 2019-10-13 01:52:13 pm

Nigel Garvey
Moderator
From:: Warwickshire, England
Registered: 2002-11-20
Posts: 5105

Re: Trying to read as list raises «error of type -116»

scrutizer82 wrote:

I can hardly grasp the difference between the end of a file and the index of the last byte of the file: don't they pertain to the same thing?


No. Sorry. I didn't explain it very clearly. The eof — the end of the file — is the insertion point immediately after the last byte in the file. Any data appended to the file have to be written from there, so we write 'starting at eof'.

The 'get eof' command returns "the length, in bytes, of a file". The person who thought up the name for the command was probably thinking of the "length" as the distance between the insertion point at the beginning of the file and the eof at end. When thought of as a count, this is the number of bytes in the file, which number is also the index of the last byte. If a write begins there, the last byte gets overwritten.

what I wanted was to append the list variable containing the value as it appears at the end of each loop cycle to the same file


In my tests, the 'read' command will only read one list from the file at a time. You can either store all your list results in a containing list and just write that to the file when you've finished, or stick to your original idea and use a repeat to read and log lists from the file like this:

Applescript:

set fref to (open for access theFile)
-- The file is now open for access with the file pointer at the beginning.
try
   -- Keep reading and logging lists from this channel until going past the eof causes an error.
   -- Each read begins at the byte immediately following the last byte of the preceding read.
   repeat
       log (read fref as list)
   end repeat
on error
   -- When the error occurs, close the access channel.
   close access fref
end try


NG

Offline

 

Board footer

Powered by FluxBB

RSS (new topics) RSS (active topics)