2015-10-06 8 views
1

Я новичок на языке Юлии, и учебник еще не очень глубокий, и я не понял, что является лучшим способом передать список параметров функции. Моя функция выглядит так:Как передать список параметров функции в Julia

function dxdt(x) 
    return a*x**2 + b*x - c 
end 

где x - переменная (2D-массив) и a, c и d - параметры. Насколько я понимаю, в Джулии не рекомендуется работать с глобальными переменными. Итак, каков правильный способ сделать это?

+3

, если список параметров является сложным, вы можете использовать [дополнительные аргументы] (HTTP: //julia.readthedocs.org/en/latest/manual/functions/# optional-arguments) и [keyword arguments] (http://julia.readthedocs.org/en/latest/manual/functions/#keyword-arguments), чтобы избежать передачи всего списка каждый раз. – Gnimuc

ответ

3

Идиоматическим решением было бы создать тип для хранения параметров и использовать несколько диспетчеров для вызова правильной версии функции.

Вот что я мог бы сделать

type Params 
    a::TypeOfA 
    b::TypeOfB 
    c::TypeOfC 
end 

function dxdt(x, p::Params) 
    p.a*x^2 + p.b*x + p.c 
end 

Иногда, если тип имеет много полей, я определяю вспомогательную функцию _unpack (или что вы хотите назвать его), который выглядит следующим образом:

_unpack(p::Params) = (p.a, p.b, p.c) 

И тогда я смог изменить осуществление dxdt быть

function dxdt(x, p::Params) 
    a, b, c = _unpack(p) 
    a*x^2 + b*x + c 
end 
+0

Что это связано с несколькими отправками? – user4235730

+0

В этом примере ничего, но если вы хотите определить другую версию 'dxdt', которая работает с другим набором параметров, вы бы все настроились на использование диспетчеризации. Я исправлю первую строку ответа – spencerlyon2

2

это вещь:

function dxdt(x, a, b, c) 
    a*x^2 + b*x + c 
    end 

или компактное определение:

dxdt(x, a, b, c) = a*x^2 + b*x + c 

смотри также argument passing in functions в документации.

+2

Спасибо за ответ, но я хотел передать только переменную x, а так или иначе получить доступ к списку параметров (у меня есть много параметров для передачи, поэтому передача всех из них в функцию будет очень неприятным кодом). Один из возможных вариантов - объявить глобальные переменные, но я понимаю, что Julia не сможет оптимизировать код со слишком большим количеством глобальных переменных. – Ohm

+1

@Ohm is [this] (http://julia.readthedocs.org/en/latest/manual/functions/# keyword-arguments) ваш прецедент? – Gnimuc

+0

@GnimucKey действительно это поможет мне, но я думаю, что я также попробую использовать его определение типа, спасибо за ваш совет! – Ohm

1

Вы действительно хотите передать экземпляр структуры данных (составной тип данных) в вашу функцию. сделать это, первый дизайн вашего типа данных:

type MyType 
    x::Vector 
    a 
    b 
    c 
end 

и реализовать dxtd функцию:

function dxdt(val::MyType) 
    return val.a*val.x^2 + val.b*val.x + val.c 
end 

тогда некоторые, где в вашем коде вы делаете экземпляр MyType, как это:

myinstance = MyType([],0.0,0.0,0.0) 

вы можете обновить myinstance

myinstance.x = [1.0,2.8,9.0] 
myinstance.a = 5 

и в конце, когда myinstance готовятся к dxxt

dxdt(myinstance) 
1

для меня это звучит, как вы ищете anonymous functions. Например:

function dxdt_parametric(x, a, b, c) 
    a*x^2 + b*x + c 
end 

a = 1 
b = 2 
c = 1 

julia> dxdt = x->dxdt_parametric(x, a, b, c) 
(anonymous function) 

julia> dxdt(3.2) 
17.64 
+0

Как быть, a, b и c являются глобальными переменными? – Davide

+1

Вы также можете сделать их константами, например, 'dxdt_parametric (x, 1, 2, 1)'. Но в целом анонимные функции еще не очень эффективны. См. Пакет FastAnonymous.jl. – tholy

2

Вы можете использовать мощь функционального языка (функции как объект первого класса и закрытие):

julia> compose_dxdt = (a,b,c) -> (x) -> a*x^2 + b*x + C#creates function with 3 parameters (a,b,c) which returns the function of x 
(anonymous function) 

julia> f1 = compose_dxdt(1,1,1) #f1 is a function with the associated values of a=1, b=1, c=1 
(anonymous function) 

julia> f1(1) 
3 

julia> f1(2) 
7 

julia> f2 = compose_dxdt(2,2,2) #f1 is a function with the associated values of a=2, b=2, c=2 
(anonymous function) 

julia> f2(1) 
6 

julia> f2(2) 
14 
Смежные вопросы