Forum: Ruby Block given to Array::join

Posted by Salvatore nashcrash (nashcrash)
on 2013-01-03 21:37
Hi.
I'm a newby in this Forum and in Ruby, but I want give my contribution.

class Array
  alias oldJoin join
  def join(sep='')
    res=self
    res=self.map {|el| yield el} if block_given?
    res.oldJoin(sep)
  end
end

What you things about-it?

Thank in advance, for any comments.
Posted by 7stud -- (7stud)
on 2013-01-03 22:09
Whoops.  Never mind.
Posted by Wayne Brissette (Guest)
on 2013-01-03 22:13
(Received via mailing list)
I'm looking for suggestions on how I might parse this data.


  addrmap_ntimc0 = insFld(foldersTree, gFld("ntimc0 @0x0.0x0.0x0", 
"ntimc0_doc.html#addrmap_ntimc0"))
    addrmap_ntimc0_ntimc_core = insFld(addrmap_ntimc0, gFld("ntimc_core 
@0x0.0x0.0x0", "ntimc0_doc.html#addrmap_ntimc0_ntimc_core"))
      reg_ntimc0_ntimc_core_CFG = insDoc(addrmap_ntimc0_ntimc_core, 
gLnk("R", "CFG @0x0.0x0.0x0", 
"ntimc0_doc.html#reg_ntimc0_ntimc_core_CFG"))

  addrmap_ntimc1 = insFld(foldersTree, gFld("ntimc1 @0x1.0x0.0x0", 
"ntimc1_doc.html#addrmap_ntimc1"))
    addrmap_ntimc1_ntimc_core = insFld(addrmap_ntimc1, gFld("ntimc_core 
@0x1.0x0.0x0", "ntimc1_doc.html#addrmap_ntimc1_ntimc_core"))
      reg_ntimc1_ntimc_core_CFG = insDoc(addrmap_ntimc1_ntimc_core, 
gLnk("R", "CFG @0x1.0x0.0x0", 
"ntimc1_doc.html#reg_ntimc1_ntimc_core_CFG"))


What I want to do is group everything starting with the line that 
includes insFld(foldersTree,

So in this abbreviated data, that would be the first line 
(addrmap_ntimc0) up to the line prior to (addrmap_ntimc1).

Normally I would use read in the file, assign it to a variable and then 
use someVariable.split(" insFld(foldersTree,")

However, in this case I want everything from the beginning of that line 
too. Any ideas? Maybe a different way to parse this data?

Thanks,
Wayne
Posted by Bartosz Dziewoński (matmarex)
on 2013-01-03 22:24
(Received via mailing list)
On Thu, 03 Jan 2013 22:13:14 +0100, Wayne Brissette <wbrisett@att.net> 
wrote:

>
> Normally I would use read in the file, assign it to a variable and then use 
someVariable.split(" insFld(foldersTree,")
>However, in this case I want everything from the beginning of that line too. Any 
ideas? Maybe a different way to parse this data?

For a very simple ugly solution, you could use a regex with lookahead.

someVariable.split(/(?= insFld\(foldersTree,)/)

This would essentially split before every occurence (as the match itself 
would be zero-width; the contents of lookahead expression are not 
matched, only its "presence").

See http://www.regular-expressions.info/lookaround.html for more :)
Posted by Robert Klemme (robert_k78)
on 2013-01-03 22:36
(Received via mailing list)
On Thu, Jan 3, 2013 at 9:37 PM, Salvatore nashcrash
<lists@ruby-forum.com> wrote:
> end
>
> What you things about-it?

I am thinking that this version is in no way better than using #map
and #join explicitly.  If you want to make this more efficient, you'd
at least have to do something like this

class Array
  def join(sep = '', &b)
    b ||= lambda {|x| x}
    s = nil

    each do |e|
      if s
        s << sep
      else
        s = ''
      end << (b[e].to_s)
    end

    s
  end
end

I am not sure though that this is such a great idea because you can
usually do this via #inject.

Kind regards

robert
Posted by Wayne Brissette (Guest)
on 2013-01-04 01:18
(Received via mailing list)
On Jan 3, 2013, at 3:23 PM, Matma Rex wrote:

> This would essentially split before every occurence (as the match itself would 
be zero-width; the contents of lookahead expression are not matched, only its 
"presence").
>
> See http://www.regular-expressions.info/lookaround.html for more :)
>

Close What this gets me is:

 insFld(foldersTree, gFld("ntimc0 @0x0.0x0.0x0", 
"ntimc0_doc.html#addrmap_ntimc0"))
addrmap_ntimc0_ntimc_core = insFld(addrmap_ntimc0, gFld("ntimc_core 
@0x0.0x0.0x0", "ntimc0_doc.html#addrmap_ntimc0_ntimc_core"))
  reg_ntimc0_ntimc_core_CFG = insDoc(addrmap_ntimc0_ntimc_core, 
gLnk("R", "CFG @0x0.0x0.0x0", 
"ntimc0_doc.html#reg_ntimc0_ntimc_core_CFG"))

  reg_ntimc0_cfg_node_node_scratch = insDoc(addrmap_ntimc0_cfg_node, 
gLnk("R", "node_scratch @0x0.0xff.0x20", 
"ntimc0_doc.html#reg_ntimc0_cfg_node_node_scratch"))
 addrmap_ntimc1 =

What I also need the start of the line (in this case addrmap_ntimc0 =  & 
the addrmap_ntimc1 would belong to the next capture array item.)

I struggled with this for a while and couldn't come up with a great 
solution. I'm hoping somebody here would have an easy fix for me. ;) 
I'll sleep on this and see what I can come up with tomorrow AM.

Thanks Matma!

Wayne
Posted by tamouse mailing lists (Guest)
on 2013-01-04 03:40
(Received via mailing list)
On Thu, Jan 3, 2013 at 6:16 PM, Wayne Brissette <wbrisett@att.net> 
wrote:
> On Jan 3, 2013, at 3:23 PM, Matma Rex wrote:
>> On Thu, 03 Jan 2013 22:13:14 +0100, Wayne Brissette <wbrisett@att.net> wrote:
>>> Normally I would use read in the file, assign it to a variable and then use 
someVariable.split(" insFld(foldersTree,")
>>> However, in this case I want everything from the beginning of that line too. 
Any ideas? Maybe a different way to parse this data?

Something like this?

data = <<-EOF
 addrmap_ntimc0 = insFld(foldersTree, gFld("ntimc0 @0x0.0x0.0x0",
"ntimc0_doc.html#addrmap_ntimc0"))
    addrmap_ntimc0_ntimc_core = insFld(addrmap_ntimc0,
gFld("ntimc_core @0x0.0x0.0x0",
"ntimc0_doc.html#addrmap_ntimc0_ntimc_core"))
      reg_ntimc0_ntimc_core_CFG = insDoc(addrmap_ntimc0_ntimc_core,
gLnk("R", "CFG @0x0.0x0.0x0",
"ntimc0_doc.html#reg_ntimc0_ntimc_core_CFG"))
…
  addrmap_ntimc1 = insFld(foldersTree, gFld("ntimc1 @0x1.0x0.0x0",
"ntimc1_doc.html#addrmap_ntimc1"))
    addrmap_ntimc1_ntimc_core = insFld(addrmap_ntimc1,
gFld("ntimc_core @0x1.0x0.0x0",
"ntimc1_doc.html#addrmap_ntimc1_ntimc_core"))
      reg_ntimc1_ntimc_core_CFG = insDoc(addrmap_ntimc1_ntimc_core,
gLnk("R", "CFG @0x1.0x0.0x0",
"ntimc1_doc.html#reg_ntimc1_ntimc_core_CFG"))
EOF

data.lines.each do |l|
  (lval,rval) = l.strip.split(/\s*=\s*/)
  p "lval=#{lval}"
  p "rval=#{rval}"

end

output:

lval=addrmap_ntimc0
rval=insFld(foldersTree, gFld("ntimc0 @0x0.0x0.0x0",
"ntimc0_doc.html#addrmap_ntimc0"))
lval=addrmap_ntimc0_ntimc_core
rval=insFld(addrmap_ntimc0, gFld("ntimc_core @0x0.0x0.0x0",
"ntimc0_doc.html#addrmap_ntimc0_ntimc_core"))
lval=reg_ntimc0_ntimc_core_CFG
rval=insDoc(addrmap_ntimc0_ntimc_core, gLnk("R", "CFG @0x0.0x0.0x0",
"ntimc0_doc.html#reg_ntimc0_ntimc_core_CFG"))
lval=…
rval=
lval=addrmap_ntimc1
rval=insFld(foldersTree, gFld("ntimc1 @0x1.0x0.0x0",
"ntimc1_doc.html#addrmap_ntimc1"))
lval=addrmap_ntimc1_ntimc_core
rval=insFld(addrmap_ntimc1, gFld("ntimc_core @0x1.0x0.0x0",
"ntimc1_doc.html#addrmap_ntimc1_ntimc_core"))
lval=reg_ntimc1_ntimc_core_CFG
rval=insDoc(addrmap_ntimc1_ntimc_core, gLnk("R", "CFG @0x1.0x0.0x0",
"ntimc1_doc.html#reg_ntimc1_ntimc_core_CFG"))


(gmail's line folding will probably mess that up, so here's a gist:
https://gist.github.com/4449464)
Posted by Wayne Brissette (Guest)
on 2013-01-04 13:03
(Received via mailing list)
Thanks tamouse and Matma. In the end I cheated. While certainly not 
pretty, or efficient , I opted for a two-pass read. First time through I 
look for a match of the "insFld(foldersTree, gFld", then I simply added 
### to the beginning of the line and replaced that in my array. During 
the next read I simply split on the three hash symbols. It's so much 
easier to split knowing what is at the beginning of a section, than text 
in the middle. ;)

Thanks again to both of you.

Wayne
Posted by Salvatore nashcrash (nashcrash)
on 2013-01-04 16:52
Robert Klemme wrote in post #1090972:
> I am thinking that this version is in no way better than using #map
> and #join explicitly.

Not better. Only simpler...
I love the elegance that you can get by

elements.join(", ") {|a| a.name}

instead of

names=elements.map {|a| a.name}
names.join(", ")

although I realize that's not a big deal... ;)

> If you want to make this more efficient, you'd
> at least have to do something like this
[cut]
> I am not sure though that this is such a great idea because you can
> usually do this via #inject.

Well, Thanks you very much for explanation and details. :)
Please log in before posting. Registration is free and takes only a minute.
Existing account (Switch to SSL-encrypted connection)
NEW: Do you have a Google/GoogleMail or Yahoo account? No registration required!
Log in with Google account | Log in with Yahoo account
No account? Register here.