从循环中的矢量中删除项目 - PARI/GP
Removing items from a vector in a loop - PARI/GP
我正在查看向量 [a,b,c],对于 [-1,0,1] 中的 a,b,c 以及函数 cycle,它将向量的每个条目移动一个到左:cycle( v ) = [v[3], v[1], v[2]]
.
我只想考虑没有两个向量是 "cycle-equivalent" 的向量;即:如果我查看向量 x、y,我不想 y = cycle( x )
.
我尝试的是设置一个向量 V,其中包含所有 27 个可能的向量,然后定义以下内容:
removecycle( V, n ) = {
local( N );
N = setsearch( V, cycle( V[n] ) );
return( V[^N] );
}
这允许我指定一个特定的向量,应用该函数,然后 return 一个新的向量和结果,如果有的话,删除。问题当然是我必须用新的向量重复这个,一次又一次地重复,让自己容易出现人为错误。
我怎样才能使它自动化?我想可以将它设置为让我的向量向量 V,测试 cycle( V[1] )
,丢弃结果,return 一个新的向量 W,然后测试 cycle( W[2] )
,等等直到所有的可能性都已经过测试。但我只是不确定如何设置它!
编辑:MNWE,为方便起见将数字更改为上面的数字。
V=[[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 1], [1, 2, 2], [1, 2, 3], [1, 3, 1], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 2], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 2], [3, 3, 3]];
vecsort(vecsort(V),are_cycles,8)
> [[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 2], [1, 2, 3], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 3]]
#vecsort(vecsort(V),are_cycles,8)
> 23
在我的例子中,我会 cycle( [1, 1, 2] ) = [2, 1, 1]
,所以我希望 [2, 1, 1]
也被删除,但这并没有发生。如前所述,我想比较器需要改进,但我不确定如何改进!
您可以通过 vecsort(_, _, 8)
在自定义比较器的帮助下删除重复项。请参阅下面的 MWE:
all_cycles(v) = [[v[3], v[1], v[2]], [v[2], v[3], v[1]]];
contains(list, value) = {
#select(n -> n == value, list) > 0
};
\ your comparator here.
are_cycles(v1, v2) = {
if(contains(all_cycles(v1), v2), 0, lex(v1, v2));
};
V = [];
vecsort(vecsort(V), are_cycles, 8)
> []
V = all_cycles([1, 2, 3]);
vecsort(vecsort(V), are_cycles, 8)
> [[2, 3, 1]]
V = concat([[1, 2, 3], [3, 2, 1]], all_cycles([1, 2, 3]));
vecsort(vecsort(V), are_cycles, 8)
> [[1, 2, 3], [3, 2, 1]]
V = concat(V, all_cycles([3, 2, 1]));
vecsort(vecsort(V), are_cycles, 8)
> [[1, 2, 3], [1, 3, 2]]
编辑: 更简单的方法是将每个元素替换为它所属的等价物 class 的代表。
现在不需要自定义比较器了。
all_cycles(v) = [v, cycle(v), cycle(cycle(v))];
representative(v) = vecsort(all_cycles(v))[1];
V=[[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 1], [1, 2, 2], [1, 2, 3], [1, 3, 1], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 2], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 2], [3, 3, 3]];
#vecsort(apply(representative, V),,8)
> 11
vecsort(apply(representative, V),,8)
> [[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 2], [1, 2, 3], [1, 3, 2], [1, 3, 3], [2, 2, 2], [2, 2, 3], [2, 3, 3], [3, 3, 3]]
我正在查看向量 [a,b,c],对于 [-1,0,1] 中的 a,b,c 以及函数 cycle,它将向量的每个条目移动一个到左:cycle( v ) = [v[3], v[1], v[2]]
.
我只想考虑没有两个向量是 "cycle-equivalent" 的向量;即:如果我查看向量 x、y,我不想 y = cycle( x )
.
我尝试的是设置一个向量 V,其中包含所有 27 个可能的向量,然后定义以下内容:
removecycle( V, n ) = {
local( N );
N = setsearch( V, cycle( V[n] ) );
return( V[^N] );
}
这允许我指定一个特定的向量,应用该函数,然后 return 一个新的向量和结果,如果有的话,删除。问题当然是我必须用新的向量重复这个,一次又一次地重复,让自己容易出现人为错误。
我怎样才能使它自动化?我想可以将它设置为让我的向量向量 V,测试 cycle( V[1] )
,丢弃结果,return 一个新的向量 W,然后测试 cycle( W[2] )
,等等直到所有的可能性都已经过测试。但我只是不确定如何设置它!
编辑:MNWE,为方便起见将数字更改为上面的数字。
V=[[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 1], [1, 2, 2], [1, 2, 3], [1, 3, 1], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 2], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 2], [3, 3, 3]];
vecsort(vecsort(V),are_cycles,8)
> [[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 2], [1, 2, 3], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 3]]
#vecsort(vecsort(V),are_cycles,8)
> 23
在我的例子中,我会 cycle( [1, 1, 2] ) = [2, 1, 1]
,所以我希望 [2, 1, 1]
也被删除,但这并没有发生。如前所述,我想比较器需要改进,但我不确定如何改进!
您可以通过 vecsort(_, _, 8)
在自定义比较器的帮助下删除重复项。请参阅下面的 MWE:
all_cycles(v) = [[v[3], v[1], v[2]], [v[2], v[3], v[1]]];
contains(list, value) = {
#select(n -> n == value, list) > 0
};
\ your comparator here.
are_cycles(v1, v2) = {
if(contains(all_cycles(v1), v2), 0, lex(v1, v2));
};
V = [];
vecsort(vecsort(V), are_cycles, 8)
> []
V = all_cycles([1, 2, 3]);
vecsort(vecsort(V), are_cycles, 8)
> [[2, 3, 1]]
V = concat([[1, 2, 3], [3, 2, 1]], all_cycles([1, 2, 3]));
vecsort(vecsort(V), are_cycles, 8)
> [[1, 2, 3], [3, 2, 1]]
V = concat(V, all_cycles([3, 2, 1]));
vecsort(vecsort(V), are_cycles, 8)
> [[1, 2, 3], [1, 3, 2]]
编辑: 更简单的方法是将每个元素替换为它所属的等价物 class 的代表。 现在不需要自定义比较器了。
all_cycles(v) = [v, cycle(v), cycle(cycle(v))];
representative(v) = vecsort(all_cycles(v))[1];
V=[[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 1], [1, 2, 2], [1, 2, 3], [1, 3, 1], [1, 3, 2], [1, 3, 3], [2, 1, 1], [2, 1, 2], [2, 1, 3], [2, 2, 1], [2, 2, 2], [2, 2, 3], [2, 3, 1], [2, 3, 2], [2, 3, 3], [3, 1, 1], [3, 1, 2], [3, 1, 3], [3, 2, 1], [3, 2, 2], [3, 2, 3], [3, 3, 1], [3, 3, 2], [3, 3, 3]];
#vecsort(apply(representative, V),,8)
> 11
vecsort(apply(representative, V),,8)
> [[1, 1, 1], [1, 1, 2], [1, 1, 3], [1, 2, 2], [1, 2, 3], [1, 3, 2], [1, 3, 3], [2, 2, 2], [2, 2, 3], [2, 3, 3], [3, 3, 3]]