Truely temporary variables

5 views
Skip to first unread message

Aaron Sherman

unread,
Apr 15, 2005, 11:45:16 AM4/15/05
to Perl6 Language List
Among the various ways of declaring variables, will Perl 6 have a way to
say, "this variable is highly temporary, and may be re-declared within
the same scope, or in a nested scope without concern"? I often find
myself doing:

my $sql = q{...};
...do some DB stuff...
my $sql = q{...};
...do more DB stuff...

This of course results in re-defining $sql, so I take out the second
"my", but then at some point I remove the first one, and strict chews me
out over not declaring $sql, so I make it "my" again.

This is a cycle I've repeated with dozens of variations on more
occasions than I care to (could?) count.

What I'd really like to say is:

throwawaytmpvar $sql = q{...};
throwawaytmpvar $sql = q{...};

without problems. Of course, "throwawaytmpvar" is a bit long, but you
get the idea.

It should probably be illegal to:

throwawaytmpvar $sql = q{...};
my $sql = q{...}; # Error: temporary became normal lexical

or for that matter even give it a new type:

throwawaytmpvar int $i = 0;
throwawaytmpvar str $i = "oops"; # Error: redefinition of type

There might be other assumptions that this implies. For example, it
might be considered always thread-private and might be required to be a
core, unboxed type. These extra assumptions are only worth it if they
enhance the optimization possibilities surrounding such a value.

--
Aaron Sherman <a...@ajs.com>
Senior Systems Engineer and Toolsmith
"It's the sound of a satellite saying, 'get me down!'" -Shriekback


Larry Wall

unread,
Apr 15, 2005, 12:10:01 PM4/15/05
to Perl6 Language List
On Fri, Apr 15, 2005 at 11:45:16AM -0400, Aaron Sherman wrote:
: Among the various ways of declaring variables, will Perl 6 have a way to

: say, "this variable is highly temporary, and may be re-declared within
: the same scope, or in a nested scope without concern"? I often find
: myself doing:
:
: my $sql = q{...};
: ...do some DB stuff...
: my $sql = q{...};
: ...do more DB stuff...
:
: This of course results in re-defining $sql, so I take out the second
: "my", but then at some point I remove the first one, and strict chews me
: out over not declaring $sql, so I make it "my" again.
:
: This is a cycle I've repeated with dozens of variations on more
: occasions than I care to (could?) count.

And at that point, why not just change it to this?

my $sql;


$sql = q{...};
...do some DB stuff...

$sql = q{...};
...do more DB stuff...

It seems to me that assignment does a pretty good job of clobbering a
variable's value without the need to redeclare the container. If you
really want to program in a definitional paradigm that requires every
new definition to have a declaration, then you ought to be giving
different definitions different names, seems like, or putting each
of them into its own scope. Or write yourself a macro. Or just turn
off the redefinition warning...

It doesn't seem to rise to the level of a new keyword for me.

Larry

Larry Wall

unread,
Apr 15, 2005, 12:17:13 PM4/15/05
to Perl6 Language List
On Fri, Apr 15, 2005 at 06:04:32PM +0200, Juerd wrote:
: No, Ucfirst it can't be, I think. And ALLCAPS is ugly. @ is taken (and
: ugly). Suggestions?

Maybe we could define an "ok" operator that suppresses only the
*first* warning produced by its argument(s). Then if you get multiple
warnings, you at least get some indication that you've overgeneralized,
even if the "wrong" warning comes out. Or maybe it only suppresses
the first warning till you get a second warning, and then it prints both.

Larry

Juerd

unread,
Apr 15, 2005, 12:04:32 PM4/15/05
to Aaron Sherman, Perl6 Language List
Aaron Sherman skribis 2005-04-15 11:45 (-0400):

> What I'd really like to say is:
> throwawaytmpvar $sql = q{...};
> throwawaytmpvar $sql = q{...};

I like the idea and propose "a", aliased "an" for this.

> It should probably be illegal to:
> throwawaytmpvar $sql = q{...};
> my $sql = q{...}; # Error: temporary became normal lexical
> or for that matter even give it a new type:
> throwawaytmpvar int $i = 0;
> throwawaytmpvar str $i = "oops"; # Error: redefinition of type

Giving it a new type should be valid. That is, I think the variable is
more useful if the old one is thrown away and a new one is created. This
can perhaps be optimized by re-using the same thing if it has no
external references anymore.

In fact,

a Str $foo = $foo;

is a nice way to indicate that from now on, you don't care about its
numeric value anymore.

All in all, I think a|an can just be my without warnings and then do
what you want.

Hm. Funny idea just occurred to me. What if something in ALLCAPS, or
better, just Ucfirst would disable all warnings for just that thing?

my $foo;
say $foo; # warning about undef $foo
Say $foo; # no warning

$closed_fh.print(Int($foo)); # just a warning about the closed fh

my $foo; # warning about new $foo masking first
My $foo; # no warning

If you think this looks much like PHP's @, you're right. It's not so bad
an idea, actually. The problem with PHP is that everything's a warning
and almost nothing actually dies.

No, Ucfirst it can't be, I think. And ALLCAPS is ugly. @ is taken (and
ugly). Suggestions?


Juerd
--
http://convolution.nl/maak_juerd_blij.html
http://convolution.nl/make_juerd_happy.html
http://convolution.nl/gajigu_juerd_n.html

Patrick R. Michaud

unread,
Apr 15, 2005, 12:21:53 PM4/15/05
to Perl6 Language List

And after the third warning, it sends you to your room with no supper.

Pm

Rod Adams

unread,
Apr 15, 2005, 12:53:49 PM4/15/05
to Perl6 Language List
Larry Wall wrote:

Wouldn't some form of trait make more sense:

my $sql = '...' is ok;

Only trick would be getting "is ok" to bind to the thing in the
preceding expression that produces the warning the programmer was
expecting. Certainly

{my $sql = '...'} is ok;

get the point across that warnings are somewhat ignorable for the block,
but that starts getting to look a lot like

{my $sql = '...'} CATCH {default};

Except that one is run-time, the other compile-time.

So one could interpret this thread as a cry for a compile-time exception
handler. I see some interesting uses for this in conjunction with
C<eval>, but I doubt I'm seeing the whole story.

-- Rod Adams

Luke Palmer

unread,
Apr 15, 2005, 1:10:52 PM4/15/05
to Aaron Sherman, Perl6 Language List
Aaron Sherman writes:
> Among the various ways of declaring variables, will Perl 6 have a way to
> say, "this variable is highly temporary, and may be re-declared within
> the same scope, or in a nested scope without concern"? I often find
> myself doing:
>
> my $sql = q{...};
> ...do some DB stuff...
> my $sql = q{...};
> ...do more DB stuff...

There's a pretty common idiom for this:

{


my $sql = q{...};

# ... do some DB stuff ...


}
{
my $sql = q{...};

# ... do more DB stuff ...
}

You see it in test suites all over the CPANdom.

Luke

Juerd

unread,
Apr 15, 2005, 1:01:27 PM4/15/05
to Rod Adams, Perl6 Language List
Rod Adams skribis 2005-04-15 11:53 (-0500):

> Wouldn't some form of trait make more sense:
> my $sql = '...' is ok;

Depends. A unary ok operator would let you pinpoint very easily,
*without* using parens:

ok $fh.print($foo); # no warnings about print (closed fh?)
# but warning about undef $foo remains

$fh.print(ok $foo); # warn about printing thingies, but not about
# undef $foo

say $foo, $bar, ok $baz, $quux; # complain about everything, except
# what has to do with $baz

my $foo;
ok my $foo = "foo $bar baz"; # warn about $bar, but not the masking
my $foo = ok "foo $bar baz"; # other way around

Chromatic

unread,
Apr 15, 2005, 2:28:02 PM4/15/05
to Perl6 Language List

Talk about a strict permission system. If that's the case, I want a
"I'm the human here, darnit!" option to bypass it.

-- c

Juerd

unread,
Apr 15, 2005, 2:22:10 PM4/15/05
to br...@brentdax.com, Perl6 Language List
Brent 'Dax' Royal-Gordon skribis 2005-04-15 11:15 (-0700):
> Anything wrong with:

Yes, moving things around breaks it, as does removing the first. There
is no real dependency on the first $sql and it'd be great if declaration
wouldn't add one.

temp $sql = q{...};


my $sql = q{...};

temp $sql = q{...};

Brent 'Dax' Royal-Gordon

unread,
Apr 15, 2005, 2:15:54 PM4/15/05
to Perl6 Language List
Aaron Sherman <a...@ajs.com> wrote:
> What I'd really like to say is:
>
> throwawaytmpvar $sql = q{...};
> throwawaytmpvar $sql = q{...};

Anything wrong with:

my $sql = q{...};

temp $sql = q{...};
temp $sql = q{...};

(Assuming C<temp> is made to work on lexicals, of course.)

--
Brent 'Dax' Royal-Gordon <br...@brentdax.com>
Perl and Parrot hacker

"I used to have a life, but I liked mail-reading so much better."

Aaron Sherman

unread,
Apr 15, 2005, 2:50:34 PM4/15/05
to Luke Palmer, Perl6 Language List

You see it all over my code too... it is always possible to simulate
many kinds of trickery that way. For example, if you want to write a
loop with a counter that is visible one statement after the loop
completes, you can say:

{
my int $i;
loop $i=0;...;$i++ {
...
}
do_stuff($i);
}

But isn't:

loop my int $i=0;...;$i++ {
...;
LAST{do_stuff($i)}
}

much cleaner? I think so, if for no other reason than it explicitly says
what it means. That's one of the reasons that LAST is so handy.

So too would my mythical declarator would prevent a few steps that are
otherwise quite easy, but cumbersome in the large.

Whatever, though. It was a simple suggestion, and seems to have sparked
FAR more controversy than the small win warrants.

Aaron Sherman

unread,
Apr 17, 2005, 6:23:14 PM4/17/05
to Juerd, Perl6 Language List
On Fri, 2005-04-15 at 18:04 +0200, Juerd wrote:
> Aaron Sherman skribis 2005-04-15 11:45 (-0400):
> > What I'd really like to say is:
> > throwawaytmpvar $sql = q{...};
> > throwawaytmpvar $sql = q{...};
>
> I like the idea and propose "a", aliased "an" for this.

Too short. Having such a short identifier does two things:

* Robs that identifier from any future possible use
* Creates incentive to use this over "my"

You want there to be a general tendency to use "my" first. If I were to
choose a word, it would be "temp" (which I think already exists, though
I forget what it does vs "my"), or "let" (to correspond with its use in
rules).

> > It should probably be illegal to:
> > throwawaytmpvar $sql = q{...};
> > my $sql = q{...}; # Error: temporary became normal lexical
> > or for that matter even give it a new type:
> > throwawaytmpvar int $i = 0;
> > throwawaytmpvar str $i = "oops"; # Error: redefinition of type
>
> Giving it a new type should be valid. That is, I think the variable is
> more useful if the old one is thrown away and a new one is created. This
> can perhaps be optimized by re-using the same thing if it has no
> external references anymore.

The reason I didn't want a new type to be valid was as an extra
precaution against problematic boilerplating. It's a minor thing, and
probably not that big a deal.


Juerd

unread,
Apr 17, 2005, 5:51:17 PM4/17/05
to Aaron Sherman, Perl6 Language List
Aaron Sherman skribis 2005-04-17 18:23 (-0400):

> On Fri, 2005-04-15 at 18:04 +0200, Juerd wrote:
> > > throwawaytmpvar $sql = q{...};
> > > throwawaytmpvar $sql = q{...};
> > I like the idea and propose "a", aliased "an" for this.
> Too short.

There is a rule of thumb, I don't know who came up with it, that says
that the length of a variable name should be proportional to its scope.
This works well, very well. The same principle can be applied to the
declaring operator, and holds for my/our already.

The usual idiom for these throwaway variables is to use blocks. The
reason to want a different way to write this, I thought was wanting to
type less, especially because it's repeated throughout code.

> * Robs that identifier from any future possible use

That's with every identifier, and if the function it provides is good
enough, this cannot be considered a problem, or we can no longer invent
any new keyword that's both short and powerful.

> * Creates incentive to use this over "my"

This is true, and the reason I now prefer a warningless my to a/an. For
this I like Larry's suggestion to use "ok", so you get "ok my $foo =
...;". Again, a short keyword, but its power warrants it, IMO.

Even if this does mean (and it does) we need something else for unit
tests.

Darren Duncan

unread,
Apr 17, 2005, 7:32:24 PM4/17/05
to Perl6 Language List
At least for the usage described in this thread, I don't see any need
at all to add new syntax to Perl 6. The existing syntax provides for
a much simpler solution yet, which also is in Perl 5.

This is the format of what I do to solve the same problem right now
in my Locale::KeyedText test suite:

my ($sql, $foo, $bar);

$sql = q{...};
...do some db stuff, also using $foo and $bar...
$sql = q{...};
...do some db stuff, also using $foo and $bar...
$sql = q{...};
...do some db stuff, also using $foo and $bar...

In other words, the simple solution is to declare the variable and
use it on SEPARATE LINES! Then you can cut/copy/paste/reorder usage
lines with impunity as you wanted.

Not only does this not require a new dubious language feature, but it
also wins for brevity.

Keep it simple, as it is said.

Reserve any new syntax for when it is genuinely useful.

-- Darren Duncan

Ashley Winters

unread,
Apr 17, 2005, 8:55:33 PM4/17/05
to Perl6 Language List
On 4/15/05, Brent 'Dax' Royal-Gordon <bren...@gmail.com> wrote:
> Aaron Sherman <a...@ajs.com> wrote:
> > What I'd really like to say is:
> >
> > throwawaytmpvar $sql = q{...};
> > throwawaytmpvar $sql = q{...};
>
> Anything wrong with:
>
> my $sql = q{...};
> temp $sql = q{...};
> temp $sql = q{...};
>
> (Assuming C<temp> is made to work on lexicals, of course.)

How about 'the'? I don't want to I<possess> the variable, I just want to use it.

the $sql = q{...};
the $sth = $dbh.prepare($sql);

It could be the same as my(), but without the posessiveness (warning)

Ashley Winters

Reply all
Reply to author
Forward
0 new messages