# 需要导入模块: import numpy [as 别名]
# 或者: from numpy import inv [as 别名]
def LS_Filter(refChannel, srvChannel, filterLen, reg=1.0, peek=10,
return_filter=False):
'''Block least squares adaptive filter. Computes filter taps using the
direct matrix inversion method.
Parameters:
refChannel: Array containing the reference channel signal
srvChannel: Array containing the surveillance channel signal
filterLen: Length of the least squares filter (in samples)
reg: L2 regularization parameter for the matrix inversion
(default 1.0)
peek: Number of noncausal filter taps. Set to zero for a
causal filter. If nonzero, clutter estimates can depend
on future values of the reference signal (this helps
sometimes)
return_filter: Boolean indicating whether to return the filter taps
Returns:
srvChannelFiltered: Surveillance channel signal with clutter removed
filterTaps: (optional) least squares filter taps
'''
if refChannel.shape != srvChannel.shape:
raise ValueError('Input vectors must have the same length')
lags = np.arange(-1*peek, filterLen)
# Create a matrix of time-shited copies of the reference channel signal
A = np.zeros((refChannel.shape[0], filterLen+peek), dtype=np.complex64)
for k in range(lags.shape[0]):
A[:, k] = np.roll(refChannel, lags[k])
# compute the autocorrelation matrix of ref
ATA = A.conj().T @ A
# create the Tikhonov regularization matrix
K = np.eye(ATA.shape[0], dtype=np.complex64)
# solve the least squares problem
filterTaps = np.linalg.solve(ATA + K*reg, A.conj().T @ srvChannel)
# direct but slightly slower implementation:
# filterTaps = np.inv(ATA + K*reg) @ A.conj().T @ srvChannel
# Apply the least squares filter to the surveillance channel
srvChannelFiltered = srvChannel - A @ filterTaps
if return_filter:
return srvChannelFiltered, filterTaps
else:
return srvChannelFiltered