You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复变量未赋值即引用问题及Python代码报错排查

Fixing Issues in FITS Cube Creation Code (Unassigned Variables & Function Call Errors)

Hey Helena, let's walk through fixing your FITS cube code step by step. I spotted a few key issues that are causing errors, including unassigned variable references and logical gaps in how you're handling the data. Here's the breakdown and corrected code:

Key Issues in the Original Code

  • Unassigned/Incorrectly Scoped Variables:
    • nonlin is calculated per file but only stores the last iteration's value. When you try to write nonlin[idx] at the end, it's a 2D array (not 3D like cube), so indexing with idx will throw an error.
    • The idx = (n>3) line inside the loop runs before all values of n are populated, which doesn't make sense—we need to filter after collecting all data.
  • Data Processing Order: You cut out the img slice after calculating nonlin, but nonlin uses the full-size image. If you want the corrected non-linear data to match the cube's cutout, you need to slice nonlin too.
  • Incomplete Function Call: The final make_cube call is missing the last parameter (y1), which will cause a positional argument error.
  • Global Variable Dependency: The coeff variable is defined outside the function, which makes the function less reusable. It's better to pass it as a parameter.

Corrected Code

from astropy.io import fits
import matplotlib.pyplot as plt
import numpy as np
import glob
import pdb # to debug

# Load coefficient data first
hdu_coeff = fits.open('MCtest_C1.fits')
print(hdu_coeff[0].header)
coeff = hdu_coeff[0].data
print(f"Coefficient shape: {coeff.shape}")
hdu_coeff.close()

filelist = glob.glob('5/img/*.fit') # Read in all fits files

def make_cube(filelist, coeff, x0, x1, y0, y1):
    num_files = len(filelist)
    exptime = np.zeros(num_files)
    n = np.zeros(num_files, dtype=int)  # Specify int dtype since n is integer
    jd = np.zeros(num_files)
    
    # Initialize arrays to hold cutout data
    cube = None
    nonlin_cube = None

    for i, name in enumerate(filelist):
        with fits.open(name) as hdu:  # Use context manager to auto-close files
            img = hdu[1].data
            # Calculate non-linear correction on full image first
            nonlin = coeff[:, :, 0] * img**3 + coeff[:, :, 1] * img**2 + coeff[:, :, 2] * img + coeff[:, :, 3]
            
            # Extract header info
            exptime[i] = hdu[0].header['EXPTIME']
            n[i] = int(hdu[0].header['RUNSET'].split(':')[0])
            jd[i] = hdu[0].header['JD']
            
            # Apply cutout to both img and nonlin
            img_cut = img[x0:x1, y0:y1]
            nonlin_cut = nonlin[x0:x1, y0:y1]
            
            # Build cube arrays
            if i == 0:
                cube = img_cut[..., np.newaxis]  # Add axis for stacking
                nonlin_cube = nonlin_cut[..., np.newaxis]
            else:
                cube = np.dstack((cube, img_cut))
                nonlin_cube = np.dstack((nonlin_cube, nonlin_cut))
            
            print(f"Run number: {n[i]}, Index: {i}, Cube shape: {cube.shape}")

    # Filter data after collecting all values
    idx = (n > 3)
    print(f"Filtered run numbers: {n[idx]}, Final cube shape: {cube[:, :, idx].shape}")

    # Write filtered data to FITS files
    # Cube
    hdu_cube = fits.PrimaryHDU(cube[:, :, idx])
    hdu_cube.writeto(f'cube_corrected_{x0}_{x1}_{y0}_{y1}.fits', overwrite=True)
    
    # Exposure time
    hdu_exptime = fits.PrimaryHDU(exptime[idx])
    hdu_exptime.writeto(f'exptime_corrected_{x0}_{x1}_{y0}_{y1}.fits', overwrite=True)
    
    # JD
    hdu_jd = fits.PrimaryHDU(jd[idx])
    hdu_jd.writeto(f'jd_corrected_{x0}_{x1}_{y0}_{y1}.fits', overwrite=True)
    
    # Non-linear correction cube
    hdu_nonlin = fits.PrimaryHDU(nonlin_cube[:, :, idx])
    hdu_nonlin.writeto(f'nonlin_corrected_{x0}_{x1}_{y0}_{y1}.fits', overwrite=True)

# Complete function call with all required parameters
make_cube(filelist, coeff, 0, 512, 0, 512)  # Replace 512 with your actual y1 value if needed

What Changed & Why

  1. Pass coeff as a Function Parameter: Makes the function self-contained instead of relying on global variables, avoiding potential scoping issues.
  2. Initialize nonlin_cube: We now build a 3D cube for the non-linear correction data, just like the image cube, so we can filter it properly with idx.
  3. Fix Data Processing Order: Cut out the image and non-linear data after calculating the correction, ensuring both match the final cube dimensions.
  4. Use Context Manager for FITS Files: with fits.open(name) as hdu automatically closes the file, preventing resource leaks.
  5. Complete Function Call: Added the missing y1 parameter (set to 512 here—adjust to your actual desired slice).
  6. Filter After Collecting All Data: Moved idx = (n>3) to after the loop, so we filter based on all run numbers, not partial data.
  7. Explicit Dtype for n: Set dtype=int since n stores integer run numbers, avoiding implicit type conversion issues.

内容的提问来源于stack exchange,提问作者helena

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 03:55:41