У меня есть фрагмент кода, который соответствует каждому вокселю в кубе данных с гауссовской плюс ненулевой наклонной линейной базовой линией.Каждый воксел представляет собой спектр излучения линии + континуума, который, в зависимости от местоположения, может быть довольно шумным, и известно, что он не ведет себя хорошо на краях изображения или спектрального диапазона.Поэтому иногда бывает необходимо установить гауссовские и линейные компоненты отдельно в тех частях спектров, где каждый из них наиболее вероятен, либо потому, что исходная подгонка не удалась, либо потому, что параметры подгонки были бессмысленными, и я могу видеть линию, которую не удалосьподходит, несмотря на шум.Я бы перешел прямо к кусочной версии, если бы мог, но разрывы могут быть проблематичными, не говоря уже о том, что это обычно более дорогая процедура с точки зрения использования времени и памяти.
Итак, моя ситуация такова: Я хочу, чтобы моя программа отвечала на несколько возможных условий, где некоторые являются исключениями (ValueError и RuntimeError), а другие - логическими или реляционными условиями, с той же процедурой .Это может быть сделано?Прямо сейчас у меня есть две копии одной и той же процедуры, одна в блоке исключений, а другая в блоке else с внутренним оператором if, и это меня раздражает.Если я не могу объединить их, есть ли способ перенаправить один или другой оператор в один и тот же блок кода без определения новой функции?
Редактировать: я изначально не включал это, потому что мои попыткиреорганизация делала беспорядок в моем коде в то время, когда я писал это.Теперь, когда я немного собрал все вместе (это все еще беспорядок, поскольку каждый протокол соответствует примерно 6 различным случаям 3 разных категорий, которые, насколько я знаю, невозможно проверить одновременно), вот соответствующийчасти моего кода:
if fitfn not in ['gauss','lorentz']:
raise IOError("Fitting function name must be 'lorentz' or 'gauss'")
cubedims=np.shape(cube)
frames=np.array([(n,w) for n,w in enumerate(wvl) if (lc-0.2<w<lc+0.2)])
#^ 3 sigma is about 27% larger than 2 fwhm
inds,wls=np.transpose(frames)
# store amplitudes of Gaussian/Lorentz profile & their errors:
fdencube=np.zeros((cubedims[1],cubedims[2]))
fduncube=np.zeros((cubedims[1],cubedims[2]))
# Store spectral index (slope) of linear continuum fit:
spindex=np.zeros((cubedims[1],cubedims[2]))
spundex=np.zeros((cubedims[1],cubedims[2]))
# Store continuum-subtracted line profiles:
lincube=np.zeros((len(frames),cubedims[1],cubedims[2]))
elincube=np.zeros((len(frames),cubedims[1],cubedims[2]))
# store line-subtracted continuum profiles:
concube=np.zeros((cubedims))
econcube=np.zeros((cubedims))
for x in xrange(cubedims[1]):
for y in xrange(cubedims[2]):
spec = cube[:,x,y]
uspec = ecube[:,x,y]
try:
p,pcov=curvf(globals()[fitfn], wvl[~np.isnan(spec)],
spec[~np.isnan(spec)],sigma=uspec[~np.isnan(spec)],
bounds = [[0.01,min(wvl),np.mean(wvl[1:]-
wvl[:-1]),-10,0.],
[50.,max(wvl),0.4,10,10.0]])
fwhm=2*abs(p[2]) if fitfn=='lorentz' else
p[2]*np.sqrt(8*np.log(2))
if (fwhm < 0.16 and (lc-0.05<p[1]<lc+0.05) and 'pcov' in
globals()):
stdp=np.sqrt(np.diag(pcov))
cvw=p[-2]*frames[:,1]+p[-1]
lincube[:,x,y]=spec[inds.astype(int)]-cvw
elincube[:,x,y]=np.sqrt(uspec[inds.astype(int)]**2+
stdp[-2]**2+stdp[-1]**2)
lvw=gauss(wvl,p[0],p[1],p[2],0,0)
concube[:,x,y]=spec-lvw
econcube[:,x,y]=np.sqrt(uspec**2+stdp[0]**2+
stdp[1]**2+stdp[2]**2)
spindex[x,y]=p[-2]
spundex[x,y]=stdp[-2]
fdencube[x,y]=p[0]
fduncube[x,y]=stdp[0]
else:
try:
s=spec[~inds.astype(int)]
u=uspec[~inds.astype(int)]
q,qcov=curvf(lreg,wls[~np.isnan(s)],s[~np.isnan(s)],
sigma=u[~np.isnan(s)],bounds = [[-10,0.],
[10,10.0]])
r,rcov=curvf(globals([fitfn],wvl[inds.astype(int)],
spec[inds.astype(int)],
sigma=uspec[inds.astype(int)],
bounds = [[0.01,min(wvl),np.mean(wvl[1:]-
wvl[:-1]),-10,0.],
[50.,max(wvl),0.4,10,10.0]])
fwhmr=2*abs(r[2]) if fitfn=='lorentz' else
r[2]*np.sqrt(8*np.log(2))
if (fwhmr < 0.16 and (lc-0.05<r[1]<lc+0.05) and 'rcov'
in globals()):
stdr=np.sqrt(np.diag(rcov))
stdq=np.sqrt(np.diag(qcov))
lvw=gauss(wvl,r[0],r[1],r[2],0,0)
concube[:,x,y]=spec-lvw
econcube[:,x,y]=np.sqrt(uspec**2+stdr[0]**2+
stdr[1]**2+stdr[2]**2)
cvw=q[0]*frames[:,1]+q[1]
lincube[:,x,y]=spec[inds.astype(int)]-cvw
elincube[:,x,y]=np.sqrt(uspec[inds.astype(int)]**2+
stdq[-2]**2+stdq[-1]**2)
spindex[x,y]=q[0]
spundex[x,y]=stdq
fdencube[x,y]=r[0]
fduncube[x,y]=stdr[0]
except (ValueError,RuntimeError):
fdencube[x,y]=np.NaN
fduncube[x,y]=np.NaN
lincube[:,x,y]=np.NaN
elincube[:,x,y]=np.NaN
try:
q,qcov=curvf(lreg,wvl[~np.isnan(spec)],
spec[~np.isnan(spec)],
sigma=uspec[~np.isnan(spec)],bounds = [[-10,0.],
[10,10.0]])
if 'qcov' in globals():
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=q[0]
spundex[x,y]=np.sqrt(np.diag(qcov))[0]
else:
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=q[0]
spundex[x,y]=np.NaN
except (ValueError,RuntimeError):
print 'fit failed'
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=np.NaN
spundex[x,y]=np.NaN
except (ValueError,RuntimeError):
try:
s=spec[~inds.astype(int)]
u=uspec[~inds.astype(int)]
q,qcov=curvf(lreg,wls[~np.isnan(s)],s[~np.isnan(s)],
sigma=u[~np.isnan(s)],bounds = [[-10,0.],
[10,10.0]])
r,rcov=curvf(globals()[fitfn],wvl[inds.astype(int)],
spec[inds.astype(int)],
sigma=uspec[inds.astype(int)],
bounds = [[0.01,min(wvl),np.mean(wvl[1:]-
wvl[:-1]),-10,0.],
[50.,max(wvl),0.4,10,10.0]])
fwhmr=2*abs(r[2]) if fitfn=='lorentz' else
r[2]*np.sqrt(8*np.log(2))
if (fwhmr < 0.16 and (lc-0.05<r[1]<lc+0.05) and 'rcov' in
globals()):
stdr=np.sqrt(np.diag(rcov))
stdq=np.sqrt(np.diag(qcov))
lvw=gauss(wvl,r[0],r[1],r[2],0,0)
concube[:,x,y]=spec-lvw
econcube[:,x,y]=np.sqrt(uspec**2+stdr[0]**2+
stdr[1]**2+stdr[2]**2)
cvw=q[0]*frames[:,1]+q[1]
lincube[:,x,y]=spec[inds.astype(int)]-cvw
elincube[:,x,y]=np.sqrt(uspec[inds.astype(int)]**2+
stdq[-2]**2+stdq[-1]**2)
spindex[x,y]=q[0]
spundex[x,y]=stdq
fdencube[x,y]=r[0]
fduncube[x,y]=stdr[0]
except (ValueError,RuntimeError):
fdencube[x,y]=np.NaN
fduncube[x,y]=np.NaN
lincube[:,x,y]=np.NaN
elincube[:,x,y]=np.NaN
try:
q,qcov=curvf(lreg,wvl[~np.isnan(spec)],
spec[~np.isnan(spec)],
sigma=uspec[~np.isnan(spec)],bounds =
[[-10,0.],[10,10.0]])
if 'qcov' in globals():
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=q[0]
spundex[x,y]=np.sqrt(np.diag(qcov))[0]
else:
print 'fit failed'
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=np.NaN
spundex[x,y]=np.NaN
except (ValueError,RuntimeError):
#if fit fails, assume it's continuum;
# continuum spectral profile doesn't matter as much
print 'fit failed'
concube[:,x,y]=spec
econcube[:,x,y]=uspec
spindex[x,y]=np.NaN
spundex[x,y]=np.NaN
Как вы можете видеть, это беспорядок дублирования, потому что я не знаю, как проверить исключения, существование переменной и сравнение переменной (если она существует) с другойПеременная все в одной строке.Я нахожусь в процессе написания модуля, который проверяет наличие переменных и выполняет логические и реляционные операции, так что если переменная не определена, возвращаемое значение всегда False, но это все равно оставляет исключения.Есть ли способ сохранить исключение?