我想知道是否有可能在julia中为变量分配自定义或现有类型而不调用它的构造函数。
类似于c ++中类的前向声明。
这是我打算实现的一个例子:
type foo
a
end
#custom type
a = foo
b = foo
#julia type, force c to be of type Int
c = Int
a.a = 5.5
b.a = 4.5
c = 6
修改澄清我的问题:
在C ++或Fortran中,通常的编码实践是在某个时刻声明变量以供以后使用。
我不记得正确的Fortran语法,但在C ++中你会写出类似的东西:
class foo;
class bar;
int a;
class foo{
private:
bar myBar;
public:
foo(int a){ myBar( a ); }
}
class bar{
public:
bar(int a){
std::cout << a << std::endl;
}
}
a = 3;
foo( a );
此代码结构的优点是它允许您在使用它们之前定义对象/类型/变量。
答案 0 :(得分:7)
您可以在全局范围中执行变量声明但不;这些是Julia中引入新scope:
的结构语言中的某些结构引入了作用域块,这些作用域是有资格成为某些变量集合范围的代码区域。变量的范围不能是任意一组源代码行;相反,它将始终与其中一个块对齐。引入这些块的构造是:
- 函数体(语法)
- while循环
- for loops
- 试试块
- catch blocks
- 终于阻止了
- let blocks
- 类型块。
值得注意的是,此列表中缺少的是开始块和if块,这些块不会引入新的范围块。
您可以选择使用type declarations:
julia> x
ERROR: UndefVarError: x not defined
julia> x::Int
ERROR: UndefVarError: x not defined
julia> begin x end # still in global scope
ERROR: UndefVarError: x not defined
julia> begin x::Int end
ERROR: UndefVarError: x not defined
julia> let x end # local scope
julia> let x; x end
ERROR: UndefVarError: x not defined
请注意,Julia会尝试将值转换为指定的类型:
julia> let
x::Int # declare variables
y::Float64 = 7 # converts (if possible)
x = y # converts (if possible)
x, y
end
(7, 7.0)
julia> function foo(x, y)
x::Int
y::Float64
z # Any
# there must be assignment for conversion to happen
x, y = x, y
z = 5im
x, y, z
end
foo (generic function with 1 method)
julia> foo(3.0, 7)
(3,7.0,0 + 5im)
julia> type Foo{T<:Number}
x::T
end
julia> type Bar
x
end
julia> immutable Baz
a
b
c
end
julia> import Base.convert
julia> convert{T<:Number}(::Type{Foo{T}}, x::Number) = Foo(T(x))
convert (generic function with 535 methods)
julia> convert(::Type{Bar}, x) = Bar(x)
convert (generic function with 536 methods)
julia> convert(::Type{Baz}, xs::NTuple{3}) = Baz(xs...)
convert (generic function with 537 methods)
julia> let
# decalre variables:
a::Foo{Int}
b::Foo{Float64}
c::Bar
d::Baz
e::Int
# assign values:
e = 42
a = e
b = e
c = string(e)
d = 'a', e, "test"
[a, b, c, d]
end
4-element Array{Any,1}:
Foo{Int64}(42)
Foo{Float64}(42.0)
Bar("42")
Baz('a',42,"test")
julia>
答案 1 :(得分:3)
在我看来,你想要做的是创建一个类型的实例而不指定内容,然后在以后填写它。这可以通过创建一个未初始化某些字段的构造函数来实现:
type Foo
a
# inner constructor that leaves all fields uninitialized
Foo() = new()
end
a = Foo()
b = Foo()
a.a = 5.5
b.a = 4.5
通过在内部构造函数中向new
提供的参数少于类型包含字段的参数,最后的参数将变为未初始化。在为未初始化的字段分配值之前读取它是错误的。
这是你追求的吗?
答案 2 :(得分:2)
没有必要在Julia中预先声明变量,因为类型只是由用法定义。
如果您想限制某些类型,那么您可以这样做:
type MyType
a::Int
end
(请注意,类型名称按惯例有初始资本。)
b = MyType(1)
c = MyType(2)
d = MyType(3.5) # error