Working with arrays

C

Clement Ow

Hi, people I know some of ya might find me familiar but, I really am
still a novice in ruby thus i'll need help once in awhile. I'd
defeinitely appreciate whatever help that is rendered! =)

ok, so back to our topic. I have a code where I would like to traverse
into files and folders and then at the same time pass in exceptions and
then after that select the whole load of files to carry out actions like
copying or deleting. But I'll only need help for the traversing of
folders and the exceptions part. Here's my code:

src1 = []
$source.each do |y|
Find.find(y + "/") do |file|
src1 << file
$file_exception.each do |ex|
src1.delete_if {|x| /#{ex}/ =~ File.basename(file)}

end
end
$source is an array of source paths like ["C:/Del", "C:/My Pictures"]
$file_exception is an array of exceptions like [".txt", ".xls"]

The whole block of code is working fine except that it traverses into
the folders twice, and then parses all the file paths into src1(which is
not what is wanted) Is there any way to improve on my code?
 
A

AzimuthDragon

I'm not an expert and I can't tell you for sure what to do here, in my own
bot I stored file contents in a variable name and then just rewrote the
file, appending whatever I needed to the end of the variables contents and
then writing the variable to the file. Anyways, back to my reason for
responding, aren't globals slow in Ruby? a friend of mine from deviantART is
always nagging about not using global variables... lol. Anyone feel like
correcting him? And why are you passing in exceptions? :?
 
D

David A. Black

Hi --

Hi, people I know some of ya might find me familiar but, I really am
still a novice in ruby thus i'll need help once in awhile. I'd
defeinitely appreciate whatever help that is rendered! =)

ok, so back to our topic. I have a code where I would like to traverse
into files and folders and then at the same time pass in exceptions and

I think you mean extensions, not exceptions.
then after that select the whole load of files to carry out actions like
copying or deleting. But I'll only need help for the traversing of
folders and the exceptions part. Here's my code:

src1 = []
$source.each do |y|
Find.find(y + "/") do |file|
src1 << file
$file_exception.each do |ex|


What is i?
src1.delete_if {|x| /#{ex}/ =~ File.basename(file)}

end
end
$source is an array of source paths like ["C:/Del", "C:/My Pictures"]
$file_exception is an array of exceptions like [".txt", ".xls"]

The whole block of code is working fine except that it traverses into
the folders twice, and then parses all the file paths into src1(which is
not what is wanted) Is there any way to improve on my code?

First, don't use global variables. They don't play nicely with
encapsulated code (i.e., code where knowledge and behavior is
encapsulated in objects which have to talk to each other, in an
orderly fashion, to get things done).

Second, I'd use File.extname rather than a pattern match on
File.basename. Something like this (semi-tested only):

source = %w{ C:/Del C:/My\ Pictures }
extensions = %w{ .txt .xls }
files = []

source.each do |s|
Find.find(s) do |file|
next if extensions.include?(File.extname(file))
files << file
end
end


David

--
Rails training from David A. Black and Ruby Power and Light:
INTRO TO RAILS June 9-12 Berlin
ADVANCING WITH RAILS June 16-19 Berlin
ADVANCING WITH RAILS July 21-24 Edison, NJ
See http://www.rubypal.com for details and updates!
 
R

Robert Klemme

2008/6/10 Clement Ow said:
ok, so back to our topic. I have a code where I would like to traverse
into files and folders and then at the same time pass in exceptions and
then after that select the whole load of files to carry out actions like
copying or deleting. But I'll only need help for the traversing of
folders and the exceptions part. Here's my code:

I pasted a solution to a this very question on May 30th (Subject "Find
files"). Didn't you see it?
http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/303503
src1 = []
$source.each do |y|
Find.find(y + "/") do |file|

The slash is not needed.
src1 << file
$file_exception.each do |ex|
src1.delete_if {|x| /#{ex}/ =~ File.basename(file)}


This is extremely inefficient since you traverse src1 over and over
again. It would be better to test the current file against the
exceptions and only put it into src1 if it is not excluded.
end
end
$source is an array of source paths like ["C:/Del", "C:/My Pictures"]
$file_exception is an array of exceptions like [".txt", ".xls"]

The whole block of code is working fine except that it traverses into
the folders twice, and then parses all the file paths into src1(which is
not what is wanted) Is there any way to improve on my code?

See above.

Cheers

robert
 
C

Clement Ow

AzimuthDragon said:
I'm not an expert and I can't tell you for sure what to do here, in my
own
bot I stored file contents in a variable name and then just rewrote the
file, appending whatever I needed to the end of the variables contents
and
then writing the variable to the file. Anyways, back to my reason for
responding, aren't globals slow in Ruby? a friend of mine from
deviantART is
always nagging about not using global variables... lol. Anyone feel like
correcting him? And why are you passing in exceptions? :?

I'm using globals because i have a config file that contains all the
path names and the different options that my program offers. I havent
heard abt global variables being slow. I think it's still manageable on
my PC.(anyway, it is gonna be run in a server during production)

Exceptions are for files that I dun wanna select. For example, like i
want to select all files in C:/DEL other than say, the .xls files. I
wont wanna list down all the .xls files, hence the need for exceptions
(my company deals with tons of files) Exceptions is used because i also
want to exclude directory names as well.


I pasted a solution to a this very question on May 30th (Subject "Find
files"). Didn't you see it?
http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/303503

Hi Robert, I did see your solution, just didnt have the time to reply..
Btw it's a sweet solution ;) just that do u think it would be possible
to incoporate multiple source paths and each source paths has an array
of file_exceptions?

Thanks for all your concearns!
 
R

Robert Klemme

2008/6/11 Clement Ow said:
Hi Robert, I did see your solution, just didnt have the time to reply..

You have time to ask questions but you do not have time to evaluate
the answers you get?
Btw it's a sweet solution ;) just that do u think it would be possible
to incoporate multiple source paths and each source paths has an array
of file_exceptions?

Yes. You just need to create a wrapper method around the one I posted.

Cheers

robert
 
C

Clement Ow

Robert said:
You have time to ask questions but you do not have time to evaluate
the answers you get?
I think i didnt explain myslef properly, I was trying out your solution,
trying to incoporate multiple source paths + file exceptions, and in the
meantime i wanted to source for other alternatives hence thhis post ;)
Yes. You just need to create a wrapper method around the one I posted.
What do you mean by wrapper method? care to explain? Thanks!
 
R

Robert Klemme

2008/6/11 Clement Ow said:
What do you mean by wrapper method? care to explain? Thanks!

A "wrapper method" wraps the other method, i.e. it calls the other
method. You can forward the block from the outer method to the inner
method like this

def f(&b)
x(&b)
end

robert
 
C

Clement Ow

Robert said:
A "wrapper method" wraps the other method, i.e. it calls the other
method. You can forward the block from the outer method to the inner
method like this

def f(&b)
x(&b)
end

robert

So what you are saying is I create a method to call another method which
is already defined? But won't it be easier to directly call the method?
Sorry, I'm abit confused here..
 
C

Clement Ow

PS: Oops, i hit submit accidentally without finishing my post
So what you are saying is I create a method to call another method which
is already defined? But won't it be easier to directly call the method?
Sorry, I'm abit confused here.. So how is it by creating a wrapper
method, I would be able to pass in multiple source and dest paths, and
exclusions?

Regards,
Clement
 
R

Robert Klemme

2008/6/12 Clement Ow said:
PS: Oops, i hit submit accidentally without finishing my post
So what you are saying is I create a method to call another method which
is already defined? But won't it be easier to directly call the method?
Sorry, I'm abit confused here.. So how is it by creating a wrapper
method, I would be able to pass in multiple source and dest paths, and
exclusions?

Separation of concerns. The innder method (the version I provided)
does the traversing and the exclusion filtering and the outer method
uses the inner method to work with multiple source directories and
exclusions.

robert
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,772
Messages
2,569,593
Members
45,111
Latest member
KetoBurn
Top