1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51

//! Simple crate that will reorder a slice based on a slice of indicies without an auxilliary array. See https://www.geeksforgeeks.org/reorder-a-array-according-to-given-indexes/

pub trait HasIndex{
	fn get(&self)->usize;
	fn set(&mut self,index:usize);
}


#[test]
fn test(){
    let mut v1:Vec<_>=(0usize..10).collect();

    let mut v2:Vec<_>=(0usize..10).rev().collect();
    v2.swap(2,7);


    impl HasIndex for usize{
        fn get(&self)->usize{
            *self
        }
        fn set(&mut self,index:usize){
            *self=index;
        }
    }
    println!("before: \n v1={:?} \n v2={:?}",v1,v2);
    
    reorder(&mut v1,&mut v2);

    println!("after: \n v1={:?} \n v2={:?}",v1,v2);
    panic!("fail");
}


pub fn reorder<'a,A:Copy,B:HasIndex>(arr:&'a mut [A],index:&mut [B])->&'a mut [A]{
	assert_eq!(arr.len(),index.len());

	for i in 0..arr.len(){
		while index[i].get()!=i{
			let old_target_i = index[index[i].get()].get();
			let old_target_e = arr[index[i].get()];

			arr[index[i].get()]=arr[i];
			index[index[i].get()].set(index[i].get());

			index[i].set(old_target_i);
			arr[i] = old_target_e;
		}
	}
	arr
}