def test_scaling(): # Test integer scaling from float # Analyze headers cannot do float-integer scaling ''' hdr = AnalyzeHeader() yield assert_true, hdr.default_x_flip shape = (1,2,3) hdr.set_data_shape(shape) hdr.set_data_dtype(np.float32) data = np.ones(shape, dtype=np.float64) S = StringIO() # Writing to float datatype doesn't need scaling write_scaled_data(hdr, data, S) rdata = read_data(hdr, S) yield assert_true, np.allclose(data, rdata) # Writing to integer datatype does, and raises an error hdr.set_data_dtype(np.int32) yield (assert_raises, HeaderTypeError, write_scaled_data, hdr, data, StringIO()) # unless we aren't scaling, in which case we convert the floats to # integers and write write_data(hdr, data, S) rdata = read_data(hdr, S) yield assert_true, np.allclose(data, rdata) # This won't work for floats that aren't close to integers data_p5 = data + 0.5 write_data(hdr, data_p5, S) rdata = read_data(hdr, S) yield assert_false, np.allclose(data_p5, rdata)
def to_files(self, files=None): ''' Write image to files passed, or self._files ''' if files is None: files = self._files if files is None: raise ValueError('Need files to write data') data = self.get_data() # Adapt header to possible two<->one file difference is_pair = files['header'] != files['image'] hdr = self.get_header().for_file_pair(is_pair) slope, inter, mn, mx = adapt_header(hdr, data) hdrf = allopen(files['header'], 'wb') hdr.write_to(hdrf) if is_pair: imgf = allopen(files['image'], 'wb') else: # single file for header and image imgf = hdrf # streams like bz2 do not allow seeks, even forward. We # check where to go, and write zeros up until the data part # of the file offset = hdr.get_data_offset() diff = offset-hdrf.tell() if diff > 0: hdrf.write('\x00' * diff) write_data(hdr, data, imgf, inter, slope, mn, mx) self._header = hdr self._files = files
def test_read_write_data(self): # Check reading and writing of data hdr = self.header_class() hdr.set_data_shape((1,2,3)) hdr.set_data_dtype(np.float32) S = StringIO() data = np.arange(6, dtype=np.float64) # data have to be the right shape yield (assert_raises, HeaderDataError, write_scaled_data, hdr, data, S) data = data.reshape((1,2,3)) # and size yield (assert_raises, HeaderDataError, write_scaled_data, hdr, data[:,:,:-1], S) yield (assert_raises, HeaderDataError, write_scaled_data, hdr, data[:,:-1,:], S) # OK if so write_scaled_data(hdr, data, S) # Read it back data_back = read_data(hdr, S) # Should be about the same yield assert_array_almost_equal, data, data_back # but with the header dtype, not the data dtype yield assert_equal, hdr.get_data_dtype(), data_back.dtype # this is with native endian, not so for swapped S2 = StringIO() hdr2 = hdr.as_byteswapped() hdr2.set_data_dtype(np.float32) hdr2.set_data_shape((1,2,3)) write_scaled_data(hdr2, data, S) data_back2 = read_data(hdr2, S) # Compares the same yield assert_array_almost_equal, data_back, data_back2 # Same dtype names yield assert_equal, data_back.dtype.name, data_back2.dtype.name # But not the same endianness yield (assert_not_equal, data.dtype.byteorder, data_back2.dtype.byteorder) # Try scaling down to integer hdr.set_data_dtype(np.uint8) S3 = StringIO() # Analyze header cannot do scaling, but, if not scaling, # AnalyzeHeader is OK write_data(hdr, data, S3) data_back = read_data(hdr, S3) yield assert_array_almost_equal, data, data_back # But, the data won't always be same as input if not scaling data = np.arange(6, dtype=np.float64).reshape((1,2,3)) + 0.5 write_data(hdr, data, S3) data_back = read_data(hdr, S3) yield assert_false, np.allclose(data, data_back)