我有一个哈希值,其值是一个大小为1
的数组:
hash = {:start => [1]}
我想解压缩数组,如:
hash.each_pair{ |key, value| hash[key] = value[0] } # => {:start=>1}
并且我认为*
- 运算符如下所示,但它没有给出预期的结果:
hash.each_pair{ |key, value| hash[key] = *value } # => {:start=>[1]}
为什么*value
会返回[1]
而不是1
?
答案 0 :(得分:3)
因为应用于[]=
的{{1}}方法除了密钥(放在hash
部分内)之外只接受一个参数,并且是一个splatted / expanded数组,这是通常,一系列值(在这种特殊情况下恰好恰好是单个元素)不能直接被接受为splatted的参数。所以它被[]
的参数接受为一个数组。
换句话说,([]=
方法的)参数必须是对象,但是splatted元素(例如[]=
)不是对象。将它们解释为对象的唯一方法是将它们放回到数组中(例如:foo, :bar, :baz
)。
使用splat运算符,您可以这样做:
[:foo, :bar, :baz]
答案 1 :(得分:3)
因为Ruby在这里表现得非常聪明。
是的,泼水操作员将"折叠"并且"展开"一个数组,但你的代码中的catch是你用这个扇形值做的。
考虑此代码:
array = ['a', 'b']
some_var = *array
array # => ['a', 'b']
正如你所看到的那样,splat运算符似乎对你的数组没有任何作用,而这个:
some_var, some_other_var = *array
some_var # => "a"
somet_other_var # => "b"
会做你期望的事情。
看来红宝石只是"数字"如果将数组展开为单个变量,则需要数组,而不是值。
编辑:正如sawa在评论中指出的那样,hash[key] =
与variable =
不同。 []=
是哈希的一个实例方法,它拥有自己的C代码,在某些情况下可能导致不同的行为(理论上)。我不知道任何例子,但这并不意味着没有。
但为了简单起见,我们可以假设常规变量赋值与hash[key] =
完全相同。
答案 2 :(得分:3)
Ruby的赋值功能无论您是分配给变量,常量还是通过赋值运算符隐式调用 int main()
{
int size,i;
cout<<"Please enter the size of the array";
cin>>size;
int *array_=new int [size];
cout<<"Please enter all elements of the array";
for(i=0;i<size;i++){
cin>>array_[i];
}
insertion(&array_,size);
return 0;
}
void insertion(int *array_[],int size){
int i;
for(i=0;i<size;i++){
cout<<*array_[i];
}
}
之类的赋值方法,都可以正常工作。为简单起见,我在以下示例中使用了变量。
在赋值中使用splat运算符解包数组,即
Hash#[]=
评估为:
a = *[1, 2, 3]
但Ruby还允许您通过列出多个值在赋值期间隐式创建数组。因此,上述内容相当于:
a = 1, 2, 3
这就是a = [1, 2, 3]
导致*[1]
的原因 - 它被解压缩,只是被转换回数组。
可以使用多个赋值分别分配元素:
[1]
或只是:
a, b = [1, 2, 3]
a #=> 1
b #=> 2
您可以在代码中使用此功能(请注意a, = [1, 2, 3]
a #=> 1
之后的逗号):
hash[key]
但是还有另一个更优雅的方法:你可以通过在数组参数周围加上括号来解包数组:
hash = {:start => [1]}
hash.each_pair { |key, values| hash[key], = values }
#=> {:start=>1}
括号将分解数组,将第一个数组元素分配给hash = {:start => [1]}
hash.each_pair { |key, (value)| hash[key] = value }
#=> {:start=>1}
。