Personally, I think it would be nicer to just have a syntax that says "create 
an array of length N by executing the following expression (typically a 
function call) N times".

Something along the lines of

    let ary = [Foo::new().., ..32];

This would be more generic, because it will work with non-Clonable values, and 
if you wanted cloned values you'd just say

    let ary = [foo.clone().., ..32];

Although if we ever get the ability to make generics that have integral 
parameters (which is necessary to implement traits on arbitrary arrays) then we 
could do this in the libraries by writing a function like I had before. 
Something like the following:

libstd/array.rs:

#[inline]
fn from_fn<T, N as uint> init(f: |uint| -> T) -> [T, ..N] {
    let mut ary: [T, ..N];
    unsafe {
        ary = intrinsics::uninit();
        for i in range(0u, N) {
            intrinsics::move_val_init(&mut ary[i], f(i));
        }
    }
    ary
}


This would let you call it like Foo(array::from_fn(|_| Zero::zero())).

-Kevin

On Nov 29, 2013, at 8:37 PM, Ashish Myles <[email protected]> wrote:

> That's some seriously nifty stuff, which got my stuff compiling again. :)
> 
> But for the long term, it would be nice to have a syntax that behaves
> as was the case with the Copy trait -- it takes a single value and
> clones it into the elements of the static array.  Or perhaps the
> developers disagree and consider it to be a niche use (static arrays
> with sizes known a-priori when writing the code) -- it would be good
> to get some clarity on this.
> 
> Thanks,
> Ashish
> 
> 
> On Fri, Nov 29, 2013 at 10:20 PM, Kevin Ballard <[email protected]> wrote:
>> If you're willing to use unsafe code and std::unstable, you can do it.
>> 
>> use std::num::Zero;
>> use std::unstable::intrinsics;
>> 
>> 
>> enum Constants {
>>    SZ = 2
>> }
>> 
>> struct Foo<T>([T, ..SZ]);
>> 
>> impl<T: Clone + DeepClone + Zero> Foo<T> {
>>    pub fn new() -> Foo<T> {
>>        let mut ary: [T, ..SZ];
>>        unsafe {
>>            ary = intrinsics::uninit();
>>            for i in range(0u, SZ as uint) {
>>                intrinsics::move_val_init(&mut ary[i], Zero::zero());
>>            }
>>        }
>>        Foo(ary)
>>    }
>> }
>> 
>> -Kevin
>> 
>> On Nov 29, 2013, at 7:05 PM, Ashish Myles <[email protected]> wrote:
>> 
>> Is there a plan to support fix-sized vector initialization without manual
>> replication?  My example is just a simplified version -- this was part of a
>> macro that takes the size as input ($n:expr) and the initialization was
>> [Zero::zero(), .. $n].  Is this use case no longer intended to be supported?
>> 
>> On Nov 29, 2013 6:47 PM, "Huon Wilson" <[email protected]> wrote:
>>> 
>>> On 30/11/13 10:33, Ashish Myles wrote:
>>>> 
>>>> Previously we had the Copy trait, which when implemented by trait T
>>>> allowed one to write
>>>> [Zero::zero(), ..SZ] where T implemented the Zero trait.  But now I am
>>>> not sure how to get that behavior.  Concretely, here is the code I
>>>> want to get compiling. (Just to check, I added both Clone and
>>>> DeepClone, even though they don't automatically allow implicit
>>>> copyability).
>>>> 
>>>> ----
>>>> use std::num::Zero;
>>>> 
>>>> enum Constants {
>>>>     SZ = 2
>>>> }
>>>> 
>>>> struct Foo<T>([T, ..SZ]);
>>>> 
>>>> impl<T : Clone + DeepClone + Zero> Foo<T> {
>>>>     pub fn new() -> Foo<T> {
>>>>         Foo([Zero::zero(), ..SZ])
>>>>     }
>>>> }
>>>> ----
>>>> 
>>>> The error I get is:
>>>> 
>>>> error: copying a value of non-copyable type `T`
>>>> tmp.rs:155         Foo([Zero::zero(), ..SZ])
>>>> 
>>>> 
>>>> Any way to do this? Or is this no longer supported for general types?
>>>> Any intentions to add this behavior again?  Otherwise, I can't even
>>>> initialize my struct while being agnostic to the specific value of SZ.
>>>> 
>>>> Ashish
>>>> _______________________________________________
>>>> Rust-dev mailing list
>>>> [email protected]
>>>> https://mail.mozilla.org/listinfo/rust-dev
>>> 
>>> 
>>> Initialising a fixed size vector [T, ..n] by [foo(), .. n] unfortunately
>>> requires that `T` is implicitly copyable (that is, it doesn't move ownership
>>> when passed by value), and there's no way around this other than [foo(),
>>> foo(), foo(),...].
>>> 
>>> 
>>> Huon
>>> _______________________________________________
>>> Rust-dev mailing list
>>> [email protected]
>>> https://mail.mozilla.org/listinfo/rust-dev
>> 
>> _______________________________________________
>> Rust-dev mailing list
>> [email protected]
>> https://mail.mozilla.org/listinfo/rust-dev
>> 
>> 

Attachment: smime.p7s
Description: S/MIME cryptographic signature

_______________________________________________
Rust-dev mailing list
[email protected]
https://mail.mozilla.org/listinfo/rust-dev

Reply via email to