Can't write to files

Ruby P.mers,

I am trying to write a script that writes to 5503 files one at a time
and then closes each file.

That is:

open a new file for read/write “w+”, process it, and then close the file
(for each of 5503 files one at a time.

The program reads in a ‘name’ file of 5503 names, uses DATA to read in
the filenames (with full path) to be opened, and a huge master file that
gets broken into the 5503 new files.

The program actually runs with no errors:

BUT DOES NOT WRITE TO INDIVIDUAL FILES!!

Before closing each file, I test to see if the file exists and it says
yes and also gives me a file size which is correct.

The master file has over 3,500,000 records so I won’t attach it.

Attached are the script and the ‘name’ files.

I should mention that I wrote a ‘brute force’ script that opens each
file by full path name (no DATA file of pathnames are used) processes
them and writes to them then closes each file and the program runs
creating the desired output (5503 files). But this is a huge script.
There has to be a better way. I can do (and have done) this in Perl.

Am I listing the filenames incorrectly.
Can I create an array of filenames and access them (iterate)?

Can you help me? Or direct me to someone who can help?

I would greatly appreciate it.

Thank you,

David Frank

301 452 3259

[email protected]

3352 Tanterra Circle

Brookeville MD 20833

David Frank wrote in post #1184818:

Ruby P.mers,

I am trying to write a script that writes to 5503 files one at a time
and then closes each file.

That is:

open a new file for read/write “w+”, process it, and then close the file
(for each of 5503 files one at a time.

The program reads in a ‘name’ file of 5503 names, uses DATA to read in
the filenames (with full path) to be opened, and a huge master file that
gets broken into the 5503 new files.

A)
I see same error in several instructions:
File.open(“fnames[j]”,“w”) do |outp|
outp[q] = File.new(“fnames[j]”,‘w+’)
ex=File.file?(“fnames[j]”)
sz=File.size?(“fnames[j]”)
File.open(‘fnames[0]’,‘r’) do |rew|

“fnames[j]” do not give the content of j cell of array ‘fnames’…
so suppress the guillemet and that will be better !

B)
you abuse of ‘!’ methodes :
a.slice!(x,y) # mean replace ‘a’ content by the slice value.
b=a.slice!(x,y) # is ambiguous
b=a[x…y] # is clear

C)
I don’t know what is “File.size?” and “File.file?”
‘?’ at end of method name mean “is it true or false ?”
==> these methods must return boolean value

You should use IRB tool, so you can test each individual
instruction/method before use them in your script.

I have tried the script with:

for j in 0…f
fname = DATA.readline
outp = File.new(“fname”,‘w+’)
ex=File.file?(“fname”)
puts ex

.....
.....
sz=File.size?("fname")
puts sz
outp.close
q = q + 1
end

END_
C:\RUBY TEST\A J ELLIS GS DOW EXTRA INN NO PCT REV.TXT
C:\RUBY TEST\A J HINCH GS DOW EXTRA INN NO PCT REV.TXT
C:\RUBY TEST\A J PIERZYNSKI GS DOW EXTRA INN NO PCT REV.TXT
C:\RUBY TEST\A J POLLOCK GS DOW EXTRA INN NO PCT REV.TXT
C:\RUBY TEST\AARON ALTHERR GS DOW EXTRA INN NO PCT REV.TXT

It still the same results the files exist and have a nonzero size but do
not show up in C:\RUBY TEST

You are writing to a file named ‘fname’. If you do a

DIR fname

you should see the file.

Remove the quotes around “fname”.

David Frank wrote in post #1184821:

I have tried the script with:

for j in 0…f
fname = DATA.readline
outp = File.new(“fname”,‘w+’)
ex=File.file?(“fname”)
puts ex

.....
.....
sz=File.size?("fname")
puts sz
outp.close
q = q + 1
end

END

try:

for j in 0…f
fname = DATA.readline
outp = File.new(fname,‘w+’)
ex=File.exists?(fname)
puts ex

.....
.....
sz=File.size(fname)
puts sz
outp.close
q = q + 1

end

Mr. Fischer,

I can’t remove the quotes. If I do remove the quotes, I get an invalid
argument error and the program stops. I am not actually writing to a
file, but using an array of files (using DATA and END, see my post
above).

I can do this in Perl using similar code.

The files are not written to any directory. Do I need to put a
statement like CHDIR RUBY TEST in my script? I you look after the
END, I list the array of filenames with the full path. By the way,
I have put 1 or 2 slashes, it still won’t write to the files.

The ‘brute force’ script runs perfectly. However this script has more
than 75,000 lines because I process each of the 5503 files (one by
one)explicitly.

David Frank
301 452 3259

Mr. Fischer,

I can’t remove the quotes. If I do remove the quotes, I get an invalid
argument error and the program stops. I am not actually writing to a
file, but using an array of files (using DATA and END, see my post
above).

I can do this in Perl using similar code.

The files are not written to any directory. Do I need to put a
statement like CHDIR RUBY TEST in my script? I you look after the
END, I list the array of filenames with the full path. By the way,
I have put 1 or 2 slashes, it still won’t write to the files.

The ‘brute force’ script runs perfectly. However this script has more
than 75,000 lines because I process each of the 5503 files (one by
one)explicitly.

David Frank
301 452 3259

The line

fname = DATA.readline

reads a line from your DATA handle and stores it in the variable fname
(BTW, it stores it including the end-of-line indicator, \n). For
instance, if your DATA line contains

C:\FOO\BAR.txt

The variable fname contains afterwards the string “C:\FOO\BAR.txt\n”.
If you would do a

outp = File.new("fname",'w+')

this would a file name named “fname”, not C:\FOO\BAR.txt. That’s why the
quotes don’t make sense. In your second version, you write

outp = File.new(fname,'w+')

and this is correct, as far as the usage of the argument goes. However,
I strongly recommend to remove the trainling newline, i.e.

outp = File.new(fname.chomp, 'w+')

Aside from this: If you get an error in your program, you need to quote
the complete error message, and show us the line, where the error
occurs.

Thank you!

I used

outp = File.new(fname.chomp, ‘w+’)

with 2 slashes in the DATA records

like this:

END_
C:\RUBY TEST\A J ELLIS GS DOW EXTRA INN NO PCT REV.TXT
C:\RUBY TEST\A J HINCH GS DOW EXTRA INN NO PCT REV.TXT

I am a novice to Ruby and never thought of the newline let alone the
chomp method.

It is running as I submit this. If there are any other problems I will
post again.

Thanks again for your help!

David Frank
301 452 3259

I am a novice to Ruby and never thought of the newline let
alone the chomp method.

.chomp by default will get rid of the trailing newline.

I think the first and major problem is for you to notice
what is going on, e. g. how your string will look like.

It was already mentioned to use irb - do it, it really
helps. But what is also very useful is if you use debug
statements as you go. You can remove them lateron.

Even tenderlove uses this way and he is a contributor
to core ruby too - here is a blog where he illustrates
the simple debugging he uses:

https://tenderlovemaking.com/2016/02/05/i-am-a-puts-debuggerer.html

It is a good read.

I also have one thing to add - while I am also a puts
debuggerer, I am also a pp debuggerer.

pp stands for pretty print.

In your scripts, do:

require 'pp'

And then, for any variable that you want to have a closer
look, do:

pp variable

especially for big hashes and arrays, pp is awesome.

I even repeat this several times in a row simply to
know where something happens, like:

pp variable
pp variable
pp variable

If you also need the name of the method and line numbers
have a look at:

LINE

and

method

and also:

caller()

If you need the stack trace. Also, you can use colours
on the commandline even on windows, I think. You can
also use bash or the older msys too - all this helps
a tiny bit.