matlab编程中的一些问题

2024-05-19 16:30

1. matlab编程中的一些问题

1、bounds=[-1;1]'得到的其实就是一个行向量[-1 1],你可以把它复制来运行一下就行了;单引号就是转置的意思,因为“;”表示“-1”和“1”是处于两行的,转置一下就回来了。
2、(bounds(:,2)-bound(:,1))是说“bounds”这个二维数组的第二列元素减去第一列元素。
3、不是。你这样就行了:
function S=bgg(x,y,z,o,p)
    。。。
    S(i)= ;或者直接S= ;
就是说你把函数中的变量,不管是向量还是矩阵,直接放在返回值处就行。甚至
m=3;S=[1 5 9 4];你想二者都返回,那么function [m,S]=bgg(x,y,z,o,p),并且主函数这样[m,S]=bgg(x,y,z,o,p),接收就行了。
4、方括号主要是把向量或矩阵的值罗列出来等功能,小括号一是表示运算优先级,二是作为引用元素的角标,三是包含函数的输入参数。

matlab编程中的一些问题

2. 简单的matlab问题

part a:
(i)循环卷积:在这里可以编写两个函数,一个是循环移位,一个是循环卷积
function y=cirshift(x,m,N)
%圆周移位
if length(x)>N
    error('N必须>=x的长度')
end
x=[x,zeros(1,N-length(x))];
n=0:N-1;
n=mod(n-m,N);
y=x(n+1);
-------------------------------------------------------------
function y=circonvt(x1,x2,N)
if length(x1)>N or length(x2)>N
    error('N必须大于或等于x的长度')
end
x1=[x1,zeros(1,N-length(x1))];
    
x2=[x2,zeros(1,N-length(x2))];
m=0:N-1;
x2=x2(mod(-m,N)+1);
H=zeros(N,N);
for n=1:N
H(n,:)=cirshift(x2,n-1,N);
end
y=x1*H';
---------------------------------------------------------------
完成这部分,调用circonvt(xn,yn),即可
(ii)线性卷积,这里就更简单了,因为都是因果信号,调用matlab自带的函数
conv(xn,yn),再用stem画出来即可
part b:
  用频域来验证part a的正确与否
 在这里用FFT ,再做IFFT即可, 我这里同样再给出一个函数:
function y=circonvt1(x1,x2,N)
%圆周卷积定理的另一种实现方法
if length(x1)>N or length(x2)>N
    error('N必须>=x的长度');
end
x1=[x1,zeros(1,N-length(x1))];
x2=[x2,zeros(1,N-length(x2))];
X1=fft(x1,N);
X2=fft(x2,N);
X=X1.*X2;
y=ifft(X,N);
y=real(y);
 两个结果相等就直接验证了循环卷积定理
当然了,这三个函数具有一般性,
_________________________________________________________________-
希望有所帮助,加油了!!! 
将上面的三个代码,分别复制到三个不同的M文件中,文件名不要变
运行:
xn=[1 -2 2 -3 -4 -4 -3 0]
yn=[0 0 2 3 5 -1 -2 -4]
mm=circonvt(xn,yn,8);
stem(mm);
nn=conv(xn,yn);
figure;
stem(nn);
ss=circonvt1(xn,yn ,8);
figure;
stem(ss); 
那个图是其中的一个:

3. 简单MATLAB问题

在Matlab中,该函数用于把矩阵中元素全下标标识转换为该元素在矩阵中对应的单下标标识。
例如:
A = [1 2 3; 4 5 6;7,8,9];
>> f=sub2ind(size(A), 2, 3)

f =

     8
即把矩阵A中第二行第三列的元素的全下标标识(2,3)转换为对应的单下标标识8,即该元素从第一列顺次数过去是第八号元素。
而ind2sub则用于把矩阵中元素单下标标识转换为该元素在矩阵中对应的全下标标识。
例如,
[i,j]=ind2sub(size(A),8)
i =
     2
j =
     3
是把矩阵A中单下标标识8的元素转换为对应的的第二行第三列全下标标识(2,3)。

简单MATLAB问题

4. 关于MATLAB的问题

一、快速傅里叶介绍
傅立叶原理表明:任何连续测量的时序或信号,都可以表示为不同频率的余弦(或正弦)波信号的无限叠加。FFT是离散傅立叶变换的快速算法,可以将一个信号变换到频域。那其在实际应用中,有哪些用途呢?
1.有些信号在时域上是很难看出什么特征的,但是如果变换到频域之后,就很容易看出特征(频率,幅值,初相位);
2.FFT可以将一个信号的频谱提取出来,进行频谱分析,为后续滤波准备;
3.通过对一个系统的输入信号和输出信号进行快速傅里叶变换后,两者进行对比,对系统可以有一个初步认识。
假设采样频率Fs,信号频率F,信号长度L,采样点数N。那么FFT之后结果就是一个为N点的复数。每一个点就对应着一个频率点。这个点的模值,就是该频率值下的幅度特性。
具体跟原始信号的幅度有什么关系呢?
1. 假设原始信号的峰值为A,那么FFT的结果的每个点(除了第一个点直流分量之外)的模值就是A的N/2倍,而第一个点就是直流分量(即0Hz),它的模值是直流分量的N倍;
2. 每个点的相位呢,就是在该频率下的信号的相位。第一个点表示直流分量,它的相位是该频率的初相位,matlab以cos为底的,若信号时正弦形式sin(t),则变成cos(t-pi/2)即可。
采样频率Fs,被N-1个点平均分成N等份,每个点的频率依次增加。为了方便进行FFT运算,通常N取大于信号长度L的2的整数次方。
例如某点n所表示的频率为:Fn=(n-1)*Fs/N。由上面的公式可以看出,Fn所能分辨到频率为为Fs/N。如果采样频率Fs为1024Hz,采样点数为1024点,则可以分辨到1Hz。
1024Hz的采样率采样1024点,刚好是1秒,也就是说,采样1秒时间的信号并做FFT,则结果可以分析到1Hz。如果采样2秒时间的信号,则N为2048,并做FFT,则结果可以分析到0.5Hz。
如果要提高频率分辨力,则必须增加采样点数,也即采样时间。频率分辨率和采样时间是倒数关系。
假设FFT之后某点n用复数a+bi表示,该复数的模就是An=sqrt(a*a+b*b),相位就是Pn=atan2(b,a)。根据以上的结果,就可以计算出n点(n≠1,且n<=N/2)对应的信号的表达式为:An/(N/2)*cos(2*pi*Fn*t+Pn),即2*An/N*cos(2*pi*Fn*t+Pn);对于n=1点的信号,是直流分量,幅度即为A1/N。
由于FFT结果的对称性,通常我们只使用前半部分的结果,即小于采样频率一半的结果。
二、例子
假设我们有一个信号,它含有5V的直流分量,频率为50Hz、相位为-30度、幅度为7V的交流信号以及一个频率为90Hz、相位为90度、幅度为3V的交流信号。数学表达式为:
x = 5 + 7*cos(2*pi*15*t - 30*pi/180) + 3*cos(2*pi*40*t - 90*pi/180)。
我们以128Hz的采样率对这个信号进行采样,总共采样256点。按照我们上面的分析,Fn=(n-1)*Fs/N,我们可以知道,每两个点之间的间距就是0.5Hz。我们的信号有3个频率:0Hz、15Hz、40Hz
出于编程方便,因为直流分量的幅值A1/N,其他点幅值为An/(N/2),故直流分量最后要除以2才是对的。
一般FFT所用数据点数N与原含有信号数据点数L相同,这样的频谱图具有较高的质量,可减小因补零或截断而产生的影响。
三、Matlab代码
Fs = 128;       % 采样频率
T = 1/Fs;       % 采样时间
L = 256;        % 信号长度
t = (0:L-1)*T; % 时间
x = 5 + 7*cos(2*pi*15*t - 30*pi/180) + 3*cos(2*pi*40*t - 90*pi/180);   %cos为底原始信号
y = x + randn(size(t));     %添加噪声
figure;
plot(t,y)
title('加噪声的信号')
xlabel('时间(s)')
快速傅里叶变换之Matlab
N = 2^nextpow2(L); %采样点数,采样点数越大,分辨的频率越精确,N>=L,超出的部分信号补为0
Y = fft(y,N)/N*2;   %除以N乘以2才是真实幅值,N越大,幅值精度越高
f = Fs/N*(0:1:N-1); %频率
A = abs(Y);     %幅值
P = angle(Y);   %相值
figure;
subplot(211);plot(f(1:N/2),A(1:N/2));   %函数fft返回值的数据结构具有对称性,因此我们只取前一半
title('幅值频谱')
xlabel('频率(Hz)')
ylabel('幅值')
subplot(212);plot(f(1:N/2),P(1:N/2));
title('相位谱频')
xlabel('频率(Hz)')
ylabel('相位')
 快速傅里叶变换之Matlab
原始信号中x = 5 + 7*cos(2*pi*15*t - 30*pi/180) + 3*cos(2*pi*40*t - 90*pi/180);
可以看到,幅值频谱中15Hz(与数学表达式中的15Hz对应),幅值7.063(与7对应),相位频谱中初相位-0.5072(与-30*pi/180对应)
幅值频谱中40Hz(与数学表达式中的40Hz对应),幅值3.082(与3对应),相位频谱中初相位-1.57(与-90*pi/180对应) 
下面验证Matlab中快速傅里叶变换是以cos为底的。
1.原始信号换为:x = 5 + 7*sin(2*pi*15*t - 30*pi/180) + 3*sin(2*pi*40*t - 90*pi/180);   %sin为底的原始信号
快速傅里叶变换之Matlab
幅值频谱明显对应正确,只需验证相位频谱。由于sin(t + p1)=cos(t + p1 - pi/2),故
-30*pi/180 - pi/2 = -2.0944,这与相位频谱中-2.093对应
-90*pi/180 - pi/2 = -3.1416,这与相位频谱中-3.057对应
若想提高结果的精度,可以提高信号长度L和采样点数N。
    2.原始信号若为x = 5 + 7*cos(2*pi*15*t - 30*pi/180) + 3*sin(2*pi*40*t - 90*pi/180);   %sin和cos为底的原始信号
同样验证正确。

5. 关于Matlab的问题,

函数seq=S_seq(100);返回前100项 
% ----用循环, 不用递归---
function seq=S_seq(n)
%数列S(n)=11*S(n-4) + 12*S(n-3) + 7*S(n-2) + 11*S(n-1)
%S(1)=1;S(2)=1;S(3)=1;S(4)=1;
if n<5
    seq = ones(n,1);
else
    seq = zeros(n,1);
    seq(1:4) = 1;
    for m=5:n
        seq(m)=11*seq(m-4)+12*seq(m-3)+7*seq(m-2)+11*seq(m-1);
    end
end

关于Matlab的问题,

6. MATLAB的问题

%第1题
%由于H=(s^2+3*s+2)/(s^3+3*s^2+4*s+12),可用下面式子:
num1=[6 0 1];den1=[1 3 3 1];
num2=[1 3 2];den2=[1 3 4 12];
G=tf(num1,den1);H=tf(num2,den2);
GH=feedback(G,H);
[z1,p1]=tf2zp(num1,den1)  %求出G的零极点
[z3,p3]=tf2zp(GH.num{1},GH.den{1})  %求出G的零极点
pzmap(GH);%画出零极点图
grid on;
%第2题
n=20;
s=0;
for i=1:n;
s=s+i^2;
end
s

>>s =

        2870
另外:
1+4+9+16...+n^2=
n*(n+1)*(2*n+1)/6

7. 关于MATLAB的问题

函数fmincon的一般调用格式为:
x = fmincon(fun,x0,A,b,Aeq,beq,lb,ub,nonlcon,options)其中fun为目标函数,x0为初值;A、b用以表示线性不等式约束,Aeq、beq用以表示线性等式约束,lb、ub表示优化变量的上下限,nonlcon表示非线性约束,options为求解选项。
 
对于你的这个例子来说,只有非线性约束,所以A、b、Aeq、beq、lb、ub这六个参数照理说不需要提供,但按照标准的调用格式,每个参数在输入参数表中都处于特定位置,所以,虽然这些参数用不上,也需要提供占位符。那6个[]就是占位符。

关于MATLAB的问题

8. MATLAB问题

1,FOUND=zeros(1,0);  定义了一个空矩阵,相当于 FOUND=[];
而FOUND = [FOUND, v]是将 v添加到原来的FOUND;
2,不是你说的那样,那两句是说,将与当前节点所在的行和列清零而已。

若满意请采纳。