Как я могу управлять индексом цикла в Юлии? - PullRequest
0 голосов
/ 05 мая 2019

Это раздел Генетического алгоритма, который кодирует в Юлии.код был написан следующим образом:

popc= [individual(rand(0:1,nvar),[]) for i in 1:nc/4,j in 1:2];
for k=1:nc/4
    #select firdt parent
    i1=rand(1:npop);
    p1=pop[i1];
    #select second parent
    i2=rand(1:npop);
    if i1==i2
        i2=rand(1:npop);
    end
    p2=pop[i2]
    #apply crossover
    m=singlepointcrossover(p1.position,p2.position);
    append!(popc[k,1].position, m[1]);
    append!(popc[k,2].position, m[2]);
end
function singlepointcrossover(x1,x2)

    nvar=length(x1);

    cutpoint=rand(1:nvar-1);

    y1=append!(x1[1:cutpoint],x2[cutpoint+1:end]);

    y2=append!(x2[1:cutpoint],x1[cutpoint+1:end]);

    return y1,y2
end

но он имеет эту ошибку.не могли бы вы помочь мне?почему это случилось?

ArgumentError: invalid index: 1.0
getindex(::Array{individual,2}, ::Float64, ::Int64) at abstractarray.jl:883
macro expansion at GA.juliarc.jl:87 [inlined]
anonymous at <missing>:?
include_string(::String, ::String) at loading.jl:522
include_string(::String, ::String, ::Int64) at eval.jl:30
include_string(::Module, ::String, ::String, ::Int64, ::Vararg{Int64,N} where N) at eval.jl:34
(::Atom.##102#107{String,Int64,String})() at eval.jl:82
withpath(::Atom.##102#107{String,Int64,String}, ::String) at utils.jl:30
withpath(::Function, ::String) at eval.jl:38
hideprompt(::Atom.##101#106{String,Int64,String}) at repl.jl:67
macro expansion at eval.jl:80 [inlined]
(::Atom.##100#105{Dict{String,Any}})() at task.jl:80

Ответы [ 2 ]

2 голосов
/ 05 мая 2019

Проблема в том, что оператор / дает результаты с плавающей запятой для целочисленных аргументов, а результаты с плавающей запятой нельзя использовать для индексации Array. Вы можете индексировать Array с помощью Integer.

/ (х, у)

Оператор правого деления: умножение x на обратное y на право. Дает результаты с плавающей запятой для целочисленных аргументов.

for k=1:nc/4

1:nc/4 создаст диапазон Float64, а k, Float64, позже будет использоваться при индексации в вашем коде на append!(popc[k,1].position, m[1]);. Поэтому вы должны сделать k и Integer.

Если nc является целым числом, вы должны использовать евклидово деление с div(nc, 4) или просто nc ÷ 4, или операторами сдвига битов nc >> 2 и nc >>> 2 (для евклидового деления на 2 ^ n вы должны сместить на n ). Все они будут давать целочисленные результаты для целочисленных аргументов.

Если nc само является числом с плавающей точкой, вам, вероятно, следует использовать один из параметров, указанных @Colin T Bowers.


popc= [individual(rand(0:1,nvar),[]) for i in 1:nc/4,j in 1:2];

У вас нет ошибки в первой строке, так как вы не используете i для индексации здесь. Еще лучше заменить nc/4 на один из перечисленных выше вариантов.

1 голос
/ 05 мая 2019

Дроби в Юлии всегда выводят Float64, даже если ответ может быть точно преобразован в Int.

Важно, что в вашем случае учтите, что Int может использоваться для индексирования массивов, а Float64 - нет.Поэтому вам нужно настроить:

for k=1:nc/2

на

for k=1:Int(nc/2)

, чтобы индекс k был типа Int, а не Float64.

Если не гарантируется, что nc будет четным целым числом, вам может потребоваться использовать floor(Int, nc/2) или ceil(Int, nc/2), в зависимости от того, что более подходит.

...