MethodError with Julia: 无法将类型为Matrix{ComplexF64}的对象进行`convert`操作。

huangapple go评论65阅读模式
英文:

MethodError with julia: cannot `convert` an object of type Matrix{ComplexF64}

问题

I was working with Scilab and I decide to work with Julia however there are some errors which I didn't arrive to solve. For instance, I would like to fill out a vector using values of a given function but I got this error. Here is the code that I used:

使用Scilab时,我决定改用Julia,但出现了一些错误,我无法解决。例如,我想要使用给定函数的值来填充一个向量,但我遇到了这个错误。以下是我使用的代码:

using LinearAlgebra
A = [5/12 -1/12; 3/4 1/4]; c=[1/3;1]; b=[3/4; 1/4];
N = 10; T = 4; ts = (0:N)*T/N;
dt = T/N; λ = 10^(-14/(2*N+1));
m=length(c) ;
em0=b'/A # b^t * inv(A)
em1 = 1 .-em0*ones(m,1)
γ(z) =@. z/(1.0 -z*em1)
u_hat=complex(zeros(1,N+1));
u_hat[1]=γ(im)

MethodError with Julia: 无法将类型为Matrix{ComplexF64}的对象进行`convert`操作。

英文:

I was working with Scilab and I decide to work with Julia however there are some errors which I didn't arrive to solve. For instance, I would like to fill out a vector using values of a given function but I got this error. Here is the code that I used:

using LinearAlgebra
A = [5/12 -1/12; 3/4 1/4];  c=[1/3;1]; b=[3/4; 1/4];
N = 10; T = 4; ts = (0:N)*T/N;
dt = T/N; λ = 10^(-14/(2*N+1));
m=length(c) ;
em0=b'/A # b^t * inv(A)
 em1 = 1 .-em0*ones(m,1)
 γ(z) =@. z/(1.0 -z*em1)
u_hat=complex(zeros(1,N+1));
u_hat[1]=γ(im)

MethodError with Julia: 无法将类型为Matrix{ComplexF64}的对象进行`convert`操作。

答案1

得分: 2

你正在面临的主要问题是,从Scilab转过来,你可能不习惯区分标量、向量和矩阵。就像在Matlab中一样,Scilab中的标量实际上是1x1矩阵,而向量实际上是Nx1或1xN矩阵。

在Julia中,情况非常不同。标量与1x1矩阵不同,向量与Nx1矩阵不同。因此,你应该小心区分它们。特别是,当你真正需要的是向量时,应该避免创建矩阵 zeros(M, 1)

错误消息的直接原因是 γ(im) 是一个矩阵,因为 em1 是一个矩阵:

julia> γ(im)
1x1 Matrix{ComplexF64}:
 0.0 + 1.0im

也是 ComplexF64 类型的矩阵,你试图将矩阵分配为其元素之一,这自然不会起作用,只有标量值可以成为 Matrix{ComplexF64} 的元素。

我在此基础上整理了你的代码:

A = [5/12 -1/12; 3/4 1/4]
# 在定义向量时使用逗号(这只是关于风格的问题)
b = [3/4, 1/4]   
N = 10

## 以下变量均未被使用,尽量将示例简化
c = [1/3, 1]  
T = 4
dt = T/N;
ts = (0:N) .* dt
λ = 10^(-14/(2*N+1))
m = length(c)
############### <- 未被使用

# 首选向量而不是1xN或Nx1矩阵
em0 = A' \ b 

# 向量与全为1的向量的点积只是求和,但非常浪费和慢。
em1 = 1 - sum(em0)

# 不要使用全局变量(!!!),并删除 `@.`
γ(z, a) = z / (1 - z * a)

# 使用向量而不是1xN矩阵,直接创建复数矩阵而不是将实矩阵转换为复数矩阵。
= zeros(ComplexF64, N+1)

# 现在这个部分可以正常工作
û[1] = γ(im, em1)

我将 `u_hat` 重命名为 `û`,仅供娱乐。

另外,请记住将你的代码放入一个函数中,这是一个好的实践。
英文:

The over-arching issue you are facing is that, coming from Scilab, you are probably not used to distinguishing scalars, vectors and matrices. Like in Matlab, Scilab scalars are really 1x1 matrices, and vectors are really Nx1 or 1xN matrices.

This is very different in Julia. A scalar is not the same as a 1x1 matrix, and a vector is not the same as a Nx1 matrix. You should therefore take care to distinguish them. In particular, you should avoid creating a matrix, zeros(M, 1), when what you really need is a vector, zeros(M).

The direct reason for the error message is that γ(im) is a matrix, because em1 is a matrix:

julia&gt; γ(im)
1&#215;1 Matrix{ComplexF64}:
 0.0 + 1.0im

u_hat is also a matrix of ComplexF64, and you are trying to assign a matrix as one of its elements, which naturally won't work, only scalar values can be elements of a Matrix{ComplexF64}.

I took the liberty of writing a cleaned up version of your code:

A = [5/12 -1/12; 3/4 1/4]
# use commas when defining vectors (this is just about style)
b = [3/4, 1/4]   
N = 10

## None of the below variables are used. Try to make your example minimal
c = [1/3, 1]  
T = 4
dt = T/N;
ts = (0:N) .* dt
λ = 10^(-14/(2*N+1))
m = length(c)
############### &lt;- not used

# prefer vectors over 1xN or Nx1 matrices
em0 = A&#39; \ b 

# dot product of a vector and a vector of ones is just a sum, but super-wasterful and slow.
em1 = 1 - sum(em0)

# don&#39;t use global variables(!!!), and remove the `@.`
γ(z, a) = z / (1 - z * a)

# use vectors, not 1xN matrices, and directly create a complex matrix instead of converting a real one.
û = zeros(ComplexF64, N+1)

# Now this works
û[1] = γ(im, em1)

I renamed u_hat to for fun.

Also: remember to put your code in a function, always.

答案2

得分: 1

问题出在你将 em1 声明为 em1 = 1 .- em0 * ones(m,1) 的地方。因为 em0 * ones(m,1) 的输出预计是标量,你可以使用 only 函数来获取它(我不反对你的方法,这超出了这个答案的范围):

julia&gt; using LinearAlgebra

# 请注意,通过这种修改,不再需要 `@.` 了。
julia&gt; γ(z) = z / (1.0 - z * em1)
γ (generic function with 1 method)

julia&gt; A = [5/12 -1/12; 3/4 1/4];  c = [1/3; 1]; b = [3/4; 1/4];
       N = 10; T = 4; ts = (0:N) * T / N;
       dt = T / N; λ = 10^(-14 / (2 * N + 1));
       m = length(c);
       em0 = b' / A;

       # 这是问题可以解决的地方
       em1 = 1 - only(em0 * ones(m, 1));

       u_hat = complex(zeros(1, N + 1));
       u_hat[1] = γ(im)
0.0 + 1.0im

julia&gt; u_hat
1×11 Matrix{ComplexF64}:
 0.0+1.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im    0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im
英文:

Just in the case of locating the root of the problem:
The problem is where you declared the em1 as em1 = 1 .-em0*ones(m,1). Since the output of the em0*ones(m,1) is expected to be a scalar, you can grasp it using the only function (I don't argue with your approach, and that's out of the interest of this answer):

julia&gt; using LinearAlgebra

# Note that with this modification, there isn&#39;t any need for `@.` anymore.
julia&gt; γ(z) = z/(1.0 -z*em1)
γ (generic function with 1 method)

julia&gt; A = [5/12 -1/12; 3/4 1/4];  c=[1/3;1]; b=[3/4; 1/4];
       N = 10; T = 4; ts = (0:N)*T/N;
       dt = T/N; λ = 10^(-14/(2*N+1));
       m=length(c);
       em0=b&#39;/A;

       #This is where the problem can be solved
       em1 = 1 - only(em0*ones(m,1));

       u_hat=complex(zeros(1,N+1));
       u_hat[1]=γ(im)
0.0 + 1.0im

julia&gt; u_hat
1&#215;11 Matrix{ComplexF64}:
 0.0+1.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im  …  0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im  0.0+0.0im

huangapple
  • 本文由 发表于 2023年2月14日 07:32:43
  • 转载请务必保留本文链接:https://go.coder-hub.com/75442141.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定