File Coverage

blib/lib/Acme/Cat/Schroedinger.pm
Criterion Covered Total %
statement 30 35 85.7
branch 7 10 70.0
condition 6 11 54.5
subroutine 9 11 81.8
pod 1 1 100.0
total 53 68 77.9


line stmt bran cond sub pod time code
1 2     2   49419 use strict;
  2         5  
  2         71  
2 2     2   12 use warnings;
  2         4  
  2         501  
3              
4             package Acme::Cat::Schroedinger;
5              
6             =head1 NAME
7              
8             Acme::Cat::Schroedinger - objects whose behaviour is determined by attempts to inspect or interact with it.
9              
10             =head1 VERSION
11              
12             1
13              
14             =cut
15              
16             our $VERSION = 1;
17              
18             use overload (
19 0     0   0 '0+' => sub {return $_[0]->('0+')->($_[0]);},
20 3     3   11 '""' => sub {return $_[0]->('""')->($_[0]);},
21 1     1   9 '@{}' => sub {return $_[0]->('@{}')->($_[0]);},
22 2     2   6 '%{}' => sub {return $_[0]->('%{}')->($_[0]);},
23 1     1   5 '${}' => sub {return $_[0]->('${}')->($_[0]);},
24 0     0   0 '*{}' => sub {return $_[0]->('*{}')->($_[0]);},
25 2     2   3438 );
  2         2288  
  2         39  
26              
27              
28             sub new{
29 8     8 1 3626 my $class = shift;
30 8         19 my %options = @_;
31             my $self = sub {
32 8     8   17 my $attr = shift;
33 8         30 my @caller = caller;
34 8 100       28 return sub {'meow'} unless $caller[0] eq __PACKAGE__;
  1         423  
35 7         34 my %attrs = (
36             'temperament' => 'cooperative', # cooperative | perverse | random
37             'kittens' => 'inherit', # inherit | default | random
38             'mutable' => '1', # 0 | 1 # never usable
39             %options
40             );
41 7 50       19 return $attrs{$attr} if exists $attrs{$attr}; # check caller
42 7 100 66     37 my $coopRef = ($attrs{temperament} eq 'cooperative' or ($attrs{temperament} eq 'random' and int(rand(2)) ) )? undef:'';
43 0 0       0 my %overload = (
44             '0+' => sub {return ($_[0]= defined $coopRef?die:0);},
45 3 100       27 '""' => sub {return ($_[0]= defined $coopRef?die:'');}, # todo: include temperament
46 1   50     11 '@{}' => sub {return ($_[0]=$coopRef // []);}, # todo: include temperament
47 2   100     18 '%{}' => sub {return ($_[0]=$coopRef // {});}, # todo: include temperament
48 1   50     9 '${}' => sub {return ($_[0]=$coopRef // \0);}, # todo: include temperament
49 0   0     0 '*{}' => sub {return ($_[0]=$coopRef // \*{''});}, # todo: include temperament
  0         0  
50 7         93 );
51 7         83 return $overload{$attr};
52 8         49 };
53 8         79 bless $self, $class;
54             }
55              
56             =head1 SYNOPSIS
57              
58             A newly-created Acme::Cat::Schroedinger could be anything. It could be cooperative, and be anything you want it to be. It could be perverse and will never be what you want it to be. Or it could behave like the original Schroedinger's Cat and its behaviour will be, for all intents and purposes, unknowable until you interact with it.
59              
60             my $cat = Acme::Cat::Schroedinger->new();
61             print %{$cat}; # The cat is now an empty hashref, and does not die.
62            
63             # or...
64             my $cat = Acme::Cat::Schroedinger->new(temperament=>'perverse');
65             print %{$cat}; # The cat is guaranteed not to be a hashref (or anything else you expect it to be), and thus will die.
66              
67             # or...
68             my $cat = Acme::Cat::Schroedinger->new(temperament=>'random');
69             print %{$cat}; # May or may not die, the only way of knowing is running the code.
70              
71             =head1 DESCRIPTION
72              
73             The Acme::Cat::Schroedinger can be 'observed' in various ways by being treated like a hashref or an arrayref or a string.
74              
75             Note that once you have observed the cat, it typically ceases to be a cat: the experiment is no longer repeatable.
76              
77             =head2 METHOD new
78              
79             my $cat = Acme::Cat::Schroedinger->new();
80              
81             When you create the cat, it has the following properties:
82              
83             =head3 temperament = cooperative
84              
85             Allowed: C. Determines whether the cat always behaves the way you ask it to, never behaves the way you ask it to, or decides how to behave only when you ask it.
86              
87             =head1 BUGS
88              
89             If you're clever, you can work out that the object in question is a cat, and furthermore you might be able to work out its temperament, mutability, etc.
90              
91             =cut
92              
93             1;