Hi. I am trying to create a program to parse a certain file. In that file is a text model of a circuit, and I want to produce a data structure that can be given to another program I've written which produces the equivalent capacitance of the circuit (so far the circuit consists solely of a batery, wire, and multiple capacitors). The data structure I want to make looks like this
# $Circ->[id][lead][index] = otherID # id is capacitor's index # lead == 0 means positive # and lead == 1 means negative # index is arbitrary (each cap may point to # several other capacitors) # otherID represents the cap's index that is # being pointed to
So a sample circuit might look like this:
# B+.............. # - . . # . C1 C2 # . . . # . . . # . ......... # . C3 # . . # ............ $Circ->[0][0][0] = 1; # Cap[0]'s positive lead connects to Cap[1] $Circ->[0][1][0] = 1; # Cap[0]'s negative lead goes to Cap[1] $Circ->[0][1][1] = 2; # Cap[0]'s negative lead goes to Cap[2] $Circ->[1][0][0] = 0; # etc. $Circ->[1][1][0] = 0; $Circ->[1][1][1] = 2; $Circ->[2][0][0] = 0; # etc. $Circ->[2][0][1] = 1; # etc. $Circ->[2][1] = (); # not pointing to anything
The code I have so far doesn't seem to work. It is recursive, and I was a little worried my algorithm might become circular and never ending. Unfortunately, it seems to only go through the first row of data. My code is below, along with the sample file that I read in. Any help is greatly appreciated. Thanks.
# read in file, make circuit ... use Data::Dumper; # 012345678901 <--(i)--> # 0 B+.....1.... # | 1 - . # (j) 2 . . # | 3 . . # 4 .........2.. open (CIRC, "circ.txt"); $cnt = 0; $i = 0; $j = 0; $on_cap = undef; while (<CIRC>) { # put elements of circuit into m-d array last if $_ =~ /=+/; chomp; $i = 0; for $char (split //, $_) { push @{$Circ->[$i++][$j]}, $char } $j++; } $i = 1; $j = 0; if ($Circ->[0][0][0] eq 'B' && $Circ->[1][0][0] eq '+' && $Circ->[0][1 +][0] eq '-') { $Circ->[0][0][0] = '.'; $Circ->[1][0][0] = '.'; $Circ->[0][1][0] = '.'; } else { die "malconfigured circuit" } $on_i = $i; $on_j = $j; &make_circ ($i,$j); sub make_circ { # count caps, make sure > 1 for $x (0..scalar @$Circ-1) { for $y (0..scalar @{$Circ->[$x]}-1) { if ($Circ->[$x][$y][0] =~ /\d/) { $cnt++ } } } goto END if $cnt <= 1; $cnt = 0; $i = $_[0]; $j = $_[1]; goto END if $ignore[$i][$j]; $looked_at[$i][$j] = 1; Iter ($i,$j); END: } sub Iter { $i = $_[0]; $j = $_[1]; $val = LookAt ($i,$j); if ($val == 0) { if ($j-1 > 0) { Iter ($i,$j-1) unless $looked_at[$i][$j-1] } if ($j+1 < scalar @{$Circ->[$i]}-1) { Iter ($i,$j+1) unless $l +ooked_at[$i][$j+1]} if ($i-1 > 0) { Iter ($i-1,$j) unless $looked_at[$i-1][$j] } if ($i+1 < scalar @$Circ-1) { Iter ($i+1,$j) unless $looked_at +[$i+1][$j] } } elsif ($val == 1) { $ignore[$i][$j] = 1; } else { for $idx (0..$#looked_at) { for (0..scalar @{$looked_at[$idx]}-1) { $looked_at[$idx][$_] = 0; } } } if (defined $on_cap) { for $id (@{$circuit->[$on_cap][0]}) { if (defined $id) { $circuit->[$id][0] = $on_cap } } # when done with Cid, replace with '.' $Circ->[$on_i][$on_j] = ['.']; $on_cap = undef; make_circ ($i,$j); } } sub LookAt { $l_i = $_[0]; $l_j = $_[1]; $cell = $Circ->[$l_i][$l_j]; if ($cell->[0] eq '.') { $ret = 0 } elsif ($cell->[0] =~ /(\d)/) { if (defined $on_cap) { push @{$circuit->[$on_cap][0]}, $1; $ret = 2 } else { $on_cap = $1; $on_i = $l_i; $on_j = $l_j; $ret = 0; } } else { $ret = 1 } return $ret; } # AND THE FILE # CIRC.TXT B+.....1.... - . . . . . .........2.. ============ 1:5 2:6

In reply to Parser Help by Anonymous Monk

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.