summaryrefslogtreecommitdiff
path: root/lib/FLAT/CMD.pm
diff options
context:
space:
mode:
Diffstat (limited to 'lib/FLAT/CMD.pm')
-rw-r--r--lib/FLAT/CMD.pm533
1 files changed, 0 insertions, 533 deletions
diff --git a/lib/FLAT/CMD.pm b/lib/FLAT/CMD.pm
deleted file mode 100644
index 5bd0e2d..0000000
--- a/lib/FLAT/CMD.pm
+++ /dev/null
@@ -1,533 +0,0 @@
-package FLAT::CMD;
-use FLAT;
-use FLAT::Regex;
-use FLAT::NFA;
-use FLAT::DFA;
-use Carp;
-
-=head1 NAME
-
-CMD - Commandline interface for the Formal Language & Automata Toolkit
-
-=head1 SYNOPSIS
-
-CMD.pm is provides an interface to the C<fash> commandline utility that offers
-certain features implemented in FLAT. Consequently, this interface is also
-available using the C<perl -MFLAT::CMD -e func> paradigm, but C<fash> makes
-things a lot more convenient.
-
-=head1 USAGE
-
-All regular language objects in FLAT implement the following methods.
-Specific regular language representations (regex, NFA, DFA) may implement
-additional methods that are outlined in the repsective POD pages.
-
-=cut
-
-# Support for perl one liners - like what CPAN.pm uses #<- should move all to another file
-use base 'Exporter'; #instead of: use Exporter (); @ISA = 'Exporter';
-use vars qw(@EXPORT $AUTOLOAD);
-
-@EXPORT = qw(compare dump dfa2gv nfa2gv pfa2gv dfa2undgv nfa2undgv pfa2undgv dfa2digraph
- nfa2digraph pfa2digraph dfa2undirected nfa2undirected pfa2undirected random_pre random_re
- savedfa test help
- );
-
-sub AUTOLOAD {
- my($l) = $AUTOLOAD;
- $l =~ s/.*:://;
- my(%EXPORT);
- @EXPORT{@EXPORT} = '';
- if (exists $EXPORT{$l}){
- FLAT::CMD->$l(@_);
- }
-}
-
-sub help {
-print <<END
-__________ .__ ___________.____ ___________
-\______ \ ___________| | \_ _____/| | _____\__ ___/
- | ___// __ \_ __ \ | | __) | | \__ \ | |
- | | \ ___/| | \/ |__ | \ | |___ / __ \| |
- |____| \___ >__| |____/ \___ / |_______ (____ /____|
- \/ \/ \/ \/
-
- Everything is wrt parallel regular expressions, i.e.,
- with the addtional shuffle operator, "&". All this
- means is that you can use the ambersand (&) as a symbol
- in the regular expressions you submit because it will be
- detected as an operator.That said, if you avoid using
- the "&" operator, you can forget about all that shuffle
- business.
-
-%perl -MFLAT::CMD -e
- "somestrings" 're1' # creates all valid strings via acyclic path, no cycles yet
- "compare 're1','re2'" # comares 2 regexs | see note [2]
- "dump 're1'" # dumps parse trees | see note[1]
- "dfa2gv 're1'" # dumps graphviz digraph desc | see note[1]
- "nfa2gv 're1'" # dumps graphviz digraph desc | see note[1]
- "pfa2gv 're1'" # dumps graphviz digraph desc | see note[1]
- "dfa2undgv 're1'" # dumps graphviz undirected graph desc | see note[1]
- "nfa2undgv 're1'" # dumps graphviz undirected graph desc | see note[1]
- "pfa2undgv 're1'" # dumps graphviz undirected graph desc | see note[1]
- "dfa2digraph 're1'" # dumps directed graph without transitions
- "nfa2digraph 're1'" # dumps directed graph without transitions
- "pfa2digraph 're1'" # dumps directed graph without transitions
- "dfa2undirected 're1'" # dumps undirected graph without transitions
- "nfa2undirected 're1'" # dumps undirected graph without transitions
- "pfa2undirected 're1'" # dumps undirected graph without transitions
- random_pre
- random_re
- "savedfa 're1'" # converts PRE to min dfa, then serializes to disk
- "test 'regex' 'string1'" # give a regex, reports if subsequent strings are valid
- help
-
-NOTES:
-[1] This means you could presumably do something like the following:
- %perl -MFLAT -e command < text_file_with_1_regex_per_line.txt
- ^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
-[2] This command compares the minimal DFAs of each regular expression;
- if there exists a exact 1-1 mapping of symbols, states, and
- transitions then the DFAs are considered equal. This means that
- "abc" will be equal to "def" To make matters more confusing, "ab+ac"
- would be equivalent to "xy+xz"; or worse yet, "z(x+y)". So to the
- 'compare' command, "ab+ac" == "xy+xz" == "z(x+y)". This however
- does not translate into the situation where "ab+ac" will accept
- the same LITERAL strings as "z(x+y)" because the symbols are obviously
- different.
-
-CREDITS:
-Blockhead, CPAN.pm (for the example of how to implement these one liners),
-and #perl on irc.freenode.net for pointing out something I missed when
-trying to copy CPAN one liner majik.
-
-Perl FLAT and all included modules are released under the same terms as Perl
-itself. Cheers.
-
-SEE:
-http://www.0x743.com/flat
-
-END
-}
-
-# save to a dat file
-sub savedfa {
- my $PRE = shift;
- # neat a better way to get input via stdin
- if (!$PRE) {
- while (<>) {
- chomp;
- $PRE = $_;
- last;
- }
- }
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- use FLAT::NFA;
- use FLAT::DFA;
- use Storable;
- # caches results, loads them in if detexted
- my $dfa = FLAT::Regex::WithExtraOps->new($PRE)->as_pfa->as_nfa->as_dfa->as_min_dfa->trim_sinks;
- store $dfa, "$PRE.dat";
-}
-
-# dumps directed graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "pfa2directed('a&b&c&d*e*')"
-sub test {
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- use FLAT::NFA;
- use FLAT::DFA;
- # handles multiple strings; first is considered the regex
- if (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new(shift @_)->as_pfa()->as_nfa->as_dfa();
- foreach (@_)
- { if ($FA->is_valid_string($_)) {
- print "(+): $_\n";
- } else {
- print "(-): $_\n";
- }
- }
- } else {
- my $FA;
- while (<STDIN>) {
- chomp;
- if ($. == 1) { #<-- uses first line as regex!
- $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa->as_dfa();
- } else {
- if ($FA->is_valid_string($_)) {
- print "(+): $_\n";
- } else {
- print "(-): $_\n";
- }
- }
- }
- }
-}
-
-# dumps parse tree
-# Usage:
-# perl -MFLAT -e "dump('re1','re2',...,'reN')"
-# perl -MFLAT -e dump < list_of_regexes.dat
-sub dump {
- use FLAT::Regex::WithExtraOps;
- use Data::Dumper;
- if (@_)
- { foreach (@_)
- { my $PRE = FLAT::Regex::WithExtraOps->new($_);
- print Dumper($PRE); }}
- else
- { while (<STDIN>)
- { chomp;
- my $PRE = FLAT::Regex::WithExtraOps->new($_);
- print Dumper($PRE); }
- }
-}
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "dfa2gv('a&b&c&d*e*')"
-sub dfa2gv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa()->as_min_dfa()->trim_sinks();
- print $FA->as_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa()->trim_sinks();
- print $FA->as_graphviz;}
- }
-}
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "nfa2gv('a&b&c&d*e*')"
-sub nfa2gv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_graphviz;}
- }
-}
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "pfa2gv('a&b&c&d*e*')"
-sub pfa2gv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_graphviz;}
- }
-}
-
-#as_undirected_graphviz
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "dfa2undgv('a&b&c&d*e*')"
-sub dfa2undgv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa()->as_min_dfa()->trim_sinks();
- print $FA->as_undirected_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa()->trim_sinks();
- print $FA->as_undirected_graphviz;}
- }
-}
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "nfa2undgv('a&b&c&d*e*')"
-sub nfa2undgv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_undirected_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_undirected_graphviz;}
- }
-}
-
-# dumps graphviz notation
-# Usage:
-# perl -MFLAT -e "pfa2undgv('a&b&c&d*e*')"
-sub pfa2undgv {
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_undirected_graphviz;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_undirected_graphviz;}
- }
-}
-
-# dumps directed graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "dfa2directed('a&b&c&d*e*')"
-sub dfa2digraph {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- # trims sink states from min-dfa since transitions are gone
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa->trim_sinks();
- print $FA->as_digraph;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa->trim_sinks();
- print $FA->as_digraph;}
- }
- print "\n";
-}
-
-# dumps directed graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "nfa2directed('a&b&c&d*e*')"
-sub nfa2digraph {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_digraph;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_digraph;}
- }
- print "\n";
-}
-
-# dumps directed graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "pfa2directed('a&b&c&d*e*')"
-sub pfa2digraph {
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_digraph;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_digraph;}
- }
- print "\n";
-}
-
-# dumps undirected graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "dfa2undirected('a&b&c&d*e*')"
-sub dfa2undirected {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- # trims sink states from min-dfa since transitions are gone
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa->trim_sinks();
- print $FA->as_undirected;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa()->as_dfa->as_min_dfa->trim_sinks();
- print $FA->as_undirected;}
- }
- print "\n";
-}
-
-# dumps undirected graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "nfa2undirected('a&b&c&d*e*')"
-sub nfa2undirected {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::NFA;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_undirected;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa()->as_nfa();
- print $FA->as_undirected;}
- }
- print "\n";
-}
-
-# dumps undirected graph using Kundu notation
-# Usage:
-# perl -MFLAT -e "pfa2undirected('a&b&c&d*e*')"
-sub pfa2undirected {
- use FLAT::Regex::WithExtraOps;
- use FLAT::PFA;
- if (@_)
- { foreach (@_)
- { my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_undirected;} }
- else
- { while (<STDIN>)
- { chomp;
- my $FA = FLAT::Regex::WithExtraOps->new($_)->as_pfa();
- print $FA->as_undirected;}
- }
- print "\n";
-}
-
-# compares 2 give PREs
-# Usage:
-# perl -MFLAT -e "compare('a','a&b&c&d*e*')" #<-- no match, btw
-sub compare {
- use FLAT::Regex::WithExtraOps;
- use FLAT::DFA;
- use FLAT::PFA;
- my $PFA1 = FLAT::Regex::WithExtraOps->new(shift)->as_pfa();
- my $PFA2 = FLAT::Regex::WithExtraOps->new(shift)->as_pfa();
- my $DFA1 = $PFA1->as_nfa->as_min_dfa;
- my $DFA2 = $PFA2->as_nfa->as_min_dfa;
- if ($DFA1->equals($DFA2)) {
- print "Yes\n";
- } else {
- print "No\n";
- }
-}
-
-# prints random PRE
-# Usage:
-# perl -MFLAT -e random_pre
-sub random_pre {
- my $and_chance = shift;
- # skirt around deep recursion warning annoyance
- local $SIG{__WARN__} = sub { $_[0] =~ /^Deep recursion/ or warn $_[0] };
- srand $$;
- my %CMDLINEOPTS = ();
- # Percent chance of each operator occuring
- $CMDLINEOPTS{LENGTH} = 32;
- $CMDLINEOPTS{OR} = 6;
- $CMDLINEOPTS{STAR} = 10;
- $CMDLINEOPTS{OPEN} = 5;
- $CMDLINEOPTS{CLOSE} = 0;
- $CMDLINEOPTS{n} = 1;
- $CMDLINEOPTS{AND} = 10; #<-- default
- $CMDLINEOPTS{AND} = $and_chance if ($and_chance == 0); #<-- to make it just an re (no shuffle)
-
-
- my $getRandomChar = sub {
- my $ch = '';
- # Get a random character between 0 and 127.
- do {
- $ch = int(rand 2);
- } while ($ch !~ m/[a-zA-Z0-9]/);
- return $ch;
- };
-
- my $getRandomRE = sub {
- my $str = '';
- my @closeparens = ();
- for (1..$CMDLINEOPTS{LENGTH}) {
- $str .= $getRandomChar->();
- # % chance of an "or"
- if (int(rand 100) < $CMDLINEOPTS{OR}) {
- $str .= "|1";
- } elsif (int(rand 100) < $CMDLINEOPTS{AND}) {
- $str .= "&0";
- } elsif (int(rand 100) < $CMDLINEOPTS{STAR}) {
- $str .= "*1";
- } elsif (int(rand 100) < $CMDLINEOPTS{OPEN}) {
- $str .= "(";
- push(@closeparens,'0101)');
- } elsif (int(rand 100) < $CMDLINEOPTS{CLOSE} && @closeparens) {
- $str .= pop(@closeparens);
- }
- }
- # empty out @closeparens if there are still some left
- if (@closeparens) {
- $str .= join('',@closeparens);
- }
- return $str;
- };
-
- for (1..$CMDLINEOPTS{n}) {
- print $getRandomRE->(),"\n";
- }
-}
-
-# prints random RE (no & operator)
-# Usage:
-# perl -MFLAT -e random_re
-sub random_re {
- shift->random_pre(0);
-}
-
-1;
-
-__END__
-
-=head1 AUTHORS & ACKNOWLEDGEMENTS
-
-FLAT is written by Mike Rosulek E<lt>mike at mikero dot comE<gt> and
-Brett Estrade E<lt>estradb at gmail dot comE<gt>.
-
-The initial version (FLAT::Legacy) by Brett Estrade was work towards an
-MS thesis at the University of Southern Mississippi.
-
-Please visit the Wiki at http://www.0x743.com/flat
-
-=head1 LICENSE
-
-This module is free software; you can redistribute it and/or modify it under
-the same terms as Perl itself.
-