Forum: Ruby Can a TkVariable store a symbol?

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
Alex D. (Guest)
on 2007-04-07 23:18
If I put a symbol into a TkVariable, it returns a string.  The following
code
illustrates this:

require 'tk'
a = TkVariable.new
a.value = :hi
puts a.value == :hi
puts a.value == "hi"

This results in

"false"
"true"

My question is, "Is this what's supposed to happen, or is this a bug?"
Wim Vander S. (Guest)
on 2007-04-08 03:16
(Received via mailing list)
On Sun, 8 Apr 2007 04:18:59 +0900
Alex DeCaria <removed_email_address@domain.invalid> wrote:

> This results in
>
> "false"
> "true"
>
> My question is, "Is this what's supposed to happen, or is this a bug?"
>

I think this is supposed to happen, as

:hi == 'hi'

also returns false.

Wim
Alex D. (Guest)
on 2007-04-08 05:30
Wim Vander S. wrote:
> On Sun, 8 Apr 2007 04:18:59 +0900
> Alex DeCaria <removed_email_address@domain.invalid> wrote:
>
>> This results in
>>
>> "false"
>> "true"
>>
>> My question is, "Is this what's supposed to happen, or is this a bug?"
>>
>
> I think this is supposed to happen, as
>
> :hi == 'hi'
>
> also returns false.
>
> Wim

Wim,

Thanks for responding.  The problem is that if you put a symbol into a
non-TkVariable, such as

b = :hi

then it stays as a symbol, and

b == :hi returns "true", while b == "hi" is "false".

But if b is a TkVariable, then the opposite occurs.  This seems
inconsistent.  I would expect that when I assign a symbol to a variable
that it won't change to a string on me arbitrarilly.  But, there may be
a good reason why it does this, and hopefully someone can explain why.

Alex
Morton G. (Guest)
on 2007-04-08 06:02
(Received via mailing list)
On Apr 7, 2007, at 3:18 PM, Alex DeCaria wrote:

>
> This results in
>
> "false"
> "true"
>
> My question is, "Is this what's supposed to happen, or is this a bug?"

It's not a bug. A TkVariable object doesn't maintain a @value
instance variable. So when you call TkVariable#value= and pass it a
symbol, the symbol will have to be coerced into something that the
underlying tcl/tk interpreter understands, which is a string. When
you call TkVariable#value, the string is retrieved from the tcl/tk
interpreter, but your TkVariable object has no memory of how the
value originated at this point.

To see how TkVariable handles different kinds of values, you can
evaluate code similar to the following:

<code>
require "tk"
v = TkVariable.new(:foo)
v.value # => "foo"
v = TkVariable.new([1, 2, 3])
v.value # => "1 2 3"
v = TkVariable.new(:foo => "red", :bar => "green")
v.value # => {"foo"=>"red", "bar"=>"green"}
</code>

Note that hashes are handled specially. Personally, I have not
encountered a situation which needed a TkVariable object that was
built on a hash, but I'm sure such situations exist. Indeed, I would
be interested if someone would post something instructive about such
situations.

Regards, Morton
Alex D. (Guest)
on 2007-04-09 03:26
Thanks Morton - That's what I needed to know.

-Alex
Hidetoshi NAGAI (Guest)
on 2007-04-09 06:25
(Received via mailing list)
From: Alex DeCaria <removed_email_address@domain.invalid>
Subject: Re: Can a TkVariable store a symbol?
Date: Mon, 9 Apr 2007 08:26:33 +0900
Message-ID: <removed_email_address@domain.invalid>
> Thanks Morton - That's what I needed to know.

TkVariable can convert Tcl's string to Ruby's object automatically.
If you want to treat a Symbol on a TkVariable,
you can set 'default_value_type' of the TkVariable object.
For example,
-------------------------------------------------------------
$ irb
irb(main):001:0> require 'tk'
=> true
irb(main):002:0> a = TkVariable.new
=> #<TkVariable: v00000>
irb(main):003:0> a.value = :hi
=> :hi
irb(main):004:0> a.value
=> "hi"
irb(main):005:0> a.symbol
=> :hi
irb(main):006:0> b = TkVariable.new(:hi, :symbol)
=> #<TkVariable: v00001>
irb(main):007:0> b.value
=> :hi
irb(main):008:0> b.string
=> "hi"
irb(main):009:0> a.default_value_type
=> nil
irb(main):010:0> b.default_value_type
=> :symbol
irb(main):011:0> a.numeric
ArgumentError: invalid value for Number: 'hi'
        from /usr/local/lib/ruby/1.8/tk/variable.rb:706:in `number'
        from /usr/local/lib/ruby/1.8/tk/variable.rb:706:in `numeric'
        from (irb):20
        from :0
irb(main):012:0> a.default_value_type = :symbol
=> :symbol
irb(main):013:0> a.value
=> :hi
irb(main):014:0> b.default_value_type = :string
=> :string
irb(main):015:0> b.value
=> "hi"
irb(main):016:0> a.value = 3
=> 3
irb(main):017:0> a.value
=> :"3"
irb(main):018:0> a.numeric
=> 3
irb(main):019:0> a.symbol
=> :"3"
irb(main):020:0> a.list
=> ["3"]
irb(main):021:0> a.numlist
=> [3]
irb(main):022:0> a.bool
=> true
irb(main):023:0> a.value = 1
=> 1
irb(main):024:0> a.bool
=> true
irb(main):025:0> a.value = 0
=> 0
irb(main):026:0> a.bool
=> false
irb(main):027:0> a.value = 'yes'
=> "yes"
irb(main):028:0> a.bool
=> true
irb(main):029:0> a.value = 'no'
=> "no"
irb(main):030:0> a.bool
=> false
irb(main):031:0> a.value = true
=> true
irb(main):032:0> a.bool
=> true
irb(main):033:0> a.value = false
=> false
irb(main):034:0> a.bool
=> false
irb(main):035:0> a.value
=> :"0"
irb(main):036:0> a.string
=> "0"
irb(main):037:0> a.value = true
=> true
irb(main):038:0> a.string
=> "1"
irb(main):039:0>
-------------------------------------------------------------

And, following operations are available too.

-------------------------------------------------------------
$ irb
irb(main):001:0> require 'tk'
=> true
irb(main):002:0> a = TkVariable.new(1)
=> #<TkVariable: v00000>
irb(main):003:0> a.value
=> "1"
irb(main):004:0> a + 1
=> 2
irb(main):005:0> a.value
=> "1"
irb(main):006:0> a + 'foo'
=> "1foo"
irb(main):007:0> a.value
=> "1"
irb(main):008:0> a.numeric += 2
=> 3
irb(main):009:0> a.value
=> "3"
irb(main):010:0> a.string += 'zzz'
=> "3zzz"
irb(main):011:0> a.value
=> "3zzz"
irb(main):012:0>
Morton G. (Guest)
on 2007-04-09 10:39
(Received via mailing list)
On Apr 8, 2007, at 10:24 PM, Hidetoshi NAGAI wrote:

> -------------------------------------------------------------
> => :hi
> irb(main):011:0> a.numeric
> => :string
> irb(main):020:0> a.list
> => 0
> irb(main):031:0> a.value = true
> => "0"
> $ irb
> irb(main):006:0> a + 'foo'
> => "3zzz"
> irb(main):012:0>
> -------------------------------------------------------------

Thank you for posting this. I learned several new things about the
capabilities of TkVariable from it.

Regards, Morton
Morton G. (Guest)
on 2007-04-09 10:59
(Received via mailing list)
On Apr 8, 2007, at 7:26 PM, Alex DeCaria wrote:

> Thanks Morton - That's what I needed to know.

As you can see from the posting by NAGAI san, there is lot more to
TkVariable than what I had worked out. Most important, of course, is
that I wasn't aware that one _can_ have the behavior that you asked
for if by making use TkVariable#default_value_type=.

Regards, Morton
This topic is locked and can not be replied to.