def test_finest_level_component_at_point(self): hg = gd.HierarchicalGridData( self.grid_data + [self.expected_data_level2] ) # Input is not a valid point with self.assertRaises(TypeError): hg.finest_level_component_at_point(0) # Dimensionality mismatch with self.assertRaises(ValueError): hg.finest_level_component_at_point([0]) # Point outside the grid with self.assertRaises(ValueError): hg.finest_level_component_at_point([1000, 200]) self.assertEqual(hg.finest_level_component_at_point([3, 4]), (2, 0)) # Test with multiple components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) self.assertCountEqual( hg3.finest_level_component_at_point([3, 4]), (0, 0) ) # Test on edge of the two components self.assertCountEqual( hg3.finest_level_component_at_point([3, 5]), (0, 0) ) self.assertCountEqual( hg3.finest_level_component_at_point([4, 6]), (0, 1) )
def test_call_evalute_with_spline(self): # Teting call is the same as evalute_with_spline hg = gd.HierarchicalGridData(self.grid_data) # Test with multiple components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) # Scalar input self.assertAlmostEqual(hg((2, 3)), 10) self.assertAlmostEqual(hg3((2, 3)), 10) # Vector input in, vector input out self.assertEqual(hg([(2, 3)]).shape, (1,)) # Scalar input that pretends to be vector self.assertAlmostEqual(hg([(2, 3)]), 10) self.assertAlmostEqual(hg3([(2, 3)]), 10) # Vector input self.assertCountEqual(hg([(2, 3), (3, 2)]), [10, 12]) self.assertCountEqual(hg3([(2, 3), (3, 2)]), [10, 12]) def product(x, y): return x * (y + 2) # Uniform grid as input grid = gd.UniformGrid([3, 5], x0=[0, 1], x1=[2, 5]) grid_data = gdu.sample_function_from_uniformgrid(product, grid) self.assertTrue(np.allclose(hg3(grid), grid_data.data))
def test_shape(self): hg = gd.HierarchicalGridData(self.grid_data) self.assertCountEqual(hg.shape, {0: 1}) # Multiple patches will throw an error hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) self.assertCountEqual(hg3.shape, {0: 2})
def test__apply_reduction(self): hg1 = gd.HierarchicalGridData(self.grid_data) self.assertAlmostEqual(hg1.min(), 0) hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) self.assertAlmostEqual(hg3.min(), 0)
def test_copy(self): hg1 = gd.HierarchicalGridData(self.grid_data) hg2 = hg1.copy() self.assertEqual(hg1, hg2) self.assertIsNot(hg1, hg2) hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) hg4 = hg3.copy() self.assertEqual(hg3, hg4)
def test_properties(self): # len hg = gd.HierarchicalGridData( self.grid_data + [self.expected_data_level2] ) self.assertEqual(len(hg), 2) # refinement levels self.assertCountEqual(hg.refinement_levels, [0, 2]) # grid_data self.assertCountEqual( hg.all_components, [self.expected_data, self.expected_data_level2] ) # first component self.assertEqual(hg.first_component, hg[0][0]) # finest level self.assertEqual(hg.num_finest_level, 2) # max refinement_level self.assertEqual(hg.max_refinement_level, 2) # coarsest level self.assertEqual(hg.num_coarsest_level, 0) # dtype self.assertEqual(hg.dtype, np.float) # x0, x1 self.assertCountEqual(hg.x0, self.expected_data.x0) self.assertCountEqual(hg.x1, self.expected_data.x1) # For multiple components there should be an error hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) with self.assertRaises(ValueError): hg3.x0 with self.assertRaises(ValueError): hg3.x1 # dx_at_level, dx coarsest, fines self.assertCountEqual(hg.dx_at_level(0), [1, 1]) self.assertCountEqual(hg3.dx_at_level(0), [1, 1]) self.assertCountEqual(hg.coarsest_dx, [1, 1]) self.assertCountEqual(hg.finest_dx, [1, 1]) # num dimensions self.assertEqual(hg.num_dimensions, 2) self.assertEqual(hg.num_extended_dimensions, 2) # time and iteration self.assertIs(hg.time, None) self.assertIs(hg.iteration, None)
def test_coordinates(self): hg_coord = gd.HierarchicalGridData(self.grid_data).coordinates() # Test with multiple components hg2_coord = gd.HierarchicalGridData( self.grid_data_two_comp ).coordinates() self.assertAlmostEqual(hg_coord[0]((2, 3)), 2) self.assertAlmostEqual(hg2_coord[0]((2, 3)), 2) self.assertAlmostEqual(hg_coord[1]((2, 3)), 3) self.assertAlmostEqual(hg2_coord[1]((2, 3)), 3)
def test_get_level(self): hg = gd.HierarchicalGridData(self.grid_data) self.assertEqual(hg.get_level(0), self.expected_data) # Level not available with self.assertRaises(ValueError): hg.get_level(10) # Multiple patches will throw an error hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) with self.assertRaises(ValueError): hg3.get_level(0)
def test_merge_refinement_levels(self): # This also tests to_UniformGridData # We redefine this to be ref_level=1 grid1 = gd.UniformGrid([4, 5], x0=[0, 1], x1=[3, 5], ref_level=1) grid2 = gd.UniformGrid([11, 21], x0=[4, 6], x1=[14, 26], ref_level=1) grids = [grid1, grid2] # Here we use the same data with another big refinement level sampled # from the same function big_grid = gd.UniformGrid( [16, 26], x0=[0, 1], x1=[30, 51], ref_level=0 ) # Big grid has resolution 2 dx of grids def product(x, y): return x * (y + 2) grid_data_two_comp = [ gdu.sample_function_from_uniformgrid(product, g) for g in grids ] big_grid_data = gdu.sample_function_from_uniformgrid(product, big_grid) hg = gd.HierarchicalGridData(grid_data_two_comp + [big_grid_data]) # When I merge the data I should just get big_grid at the resolution # of self.grid_data_two_comp expected_grid = gd.UniformGrid( [31, 51], x0=[0, 1], x1=[30, 51], ref_level=-1 ) expected_data = gdu.sample_function_from_uniformgrid( product, expected_grid ) # Test with resample self.assertEqual( hg.merge_refinement_levels(resample=True), expected_data ) # If we don't resample there will be points that are "wrong" because we # compute them with the nearest neighbors of the lowest resolution grid # For example, the point with coordinate (5, 1) falls inside the lowest # resolution grid, so its value will be the value of the closest point # in big_grid (6, 1) -> 18. self.assertEqual(hg.merge_refinement_levels()((5, 1)), 18) self.assertEqual(hg.merge_refinement_levels().grid, expected_grid) # Test a case with only one refinement level, so just returning a copy hg_one = gd.HierarchicalGridData([big_grid_data]) self.assertEqual(hg_one.merge_refinement_levels(), big_grid_data)
def test_init(self): # Test incorrect arguments # Not a list with self.assertRaises(TypeError): gd.HierarchicalGridData(0) # Empty list with self.assertRaises(ValueError): gd.HierarchicalGridData([]) # Not a list of UniformGridData with self.assertRaises(TypeError): gd.HierarchicalGridData([0]) # Inconsistent number of dimensions def product1(x): return x def product2(x, y): return x * y prod_data1 = gdu.sample_function(product1, [101], [0], [3]) prod_data2 = gdu.sample_function(product2, [101, 101], [0, 0], [3, 3]) with self.assertRaises(ValueError): gd.HierarchicalGridData([prod_data1, prod_data2]) # Only one component one = gd.HierarchicalGridData([prod_data1]) # Test content self.assertDictEqual( one.grid_data_dict, {-1: [prod_data1.ghost_zones_removed()]} ) grid = gd.UniformGrid([101], x0=[0], x1=[3], ref_level=2) # Two components at two different levels prod_data1_level2 = gdu.sample_function_from_uniformgrid( product1, grid ) two = gd.HierarchicalGridData([prod_data1, prod_data1_level2]) self.assertDictEqual( two.grid_data_dict, { -1: [prod_data1.ghost_zones_removed()], 2: [prod_data1_level2.ghost_zones_removed()], }, ) # Test a good grid hg_many_components = gd.HierarchicalGridData(self.grid_data) self.assertEqual( hg_many_components.grid_data_dict[0], [self.expected_data] ) # Test a grid with two separate components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) self.assertEqual(hg3.grid_data_dict[0], self.grid_data_two_comp)
def setUp(self): # Let's test with a TimeSeries, a UniformGridData, and a # HierarchicalGridData x = np.linspace(0, 2 * np.pi, 100) y = np.sin(x) self.TS = ts.TimeSeries(x, y) self.grid_2d = gd.UniformGrid([10, 20], x0=[0.5, 1], dx=[1, 1]) self.ugd = gdu.sample_function_from_uniformgrid( lambda x, y: x * (y + 2), self.grid_2d) grid_2d_1 = gd.UniformGrid([10, 20], x0=[0.5, 1], dx=[1, 1], ref_level=0) self.ugd1 = gdu.sample_function_from_uniformgrid( lambda x, y: x * (y + 2), grid_2d_1) grid_2d_2 = gd.UniformGrid([10, 20], x0=[1, 2], dx=[3, 0.4], ref_level=1) self.ugd2 = gdu.sample_function_from_uniformgrid( lambda x, y: x * (y + 2), grid_2d_2) self.hg = gd.HierarchicalGridData([self.ugd1, self.ugd2])
def test_str(self): hg = gd.HierarchicalGridData(self.grid_data_two_comp) expected_str = "Available refinement levels (components):\n" expected_str += "0 (2)\n" expected_str += "Spacing at coarsest level (0): [1. 1.]\n" expected_str += "Spacing at finest level (0): [1. 1.]" self.assertEqual(expected_str, hg.__str__())
def test__apply_binary(self): hg1 = gd.HierarchicalGridData(self.grid_data) # Test incompatible types with self.assertRaises(TypeError): hg1 + "hey" def neg_product(x, y): return -x * (y + 2) neg_data = gdu.sample_function_from_uniformgrid( neg_product, self.expected_grid ) hg2 = gd.HierarchicalGridData([neg_data]) zero = hg1 + hg2 zero += 0 # To check that zero is indeed zero we check that the abs max of the # data is 0 self.assertEqual(np.amax(np.abs(zero[0][0].data)), 0) # Test incompatible refinement levels neg_data_level2 = gdu.sample_function_from_uniformgrid( neg_product, self.expected_grid_level2 ) with self.assertRaises(ValueError): hg1 + gd.HierarchicalGridData([neg_data_level2]) # Test with multiple components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) hg4 = hg3.copy() hg4[0][0] *= -1 hg4[0][1] *= -1 zero2 = hg3 + hg4 self.assertEqual(np.amax(np.abs(zero2[0][0].data)), 0) self.assertEqual(np.amax(np.abs(zero2[0][1].data)), 0)
def test_plot_components_boundaries(self): # Test invalid data with self.assertRaises(TypeError): viz.plot_components_boundaries("bob") # Not 2D data ugd1D = gdu.sample_function(lambda x: x, [10], [0], [2]) hg1D = gd.HierarchicalGridData([ugd1D]) # Test invalid data with self.assertRaises(ValueError): viz.plot_components_boundaries(hg1D) # Now with valid data ugd = gdu.sample_function(lambda x, y: x + y, [10, 20], [0, 2], [2, 5]) hg = gd.HierarchicalGridData([ugd]) viz.plot_components_boundaries(hg)
def test_iter(self): hg1 = gd.HierarchicalGridData(self.grid_data) for ref_level, comp, data in hg1: self.assertTrue(isinstance(data, gd.UniformGridData)) self.assertEqual(ref_level, 0) self.assertEqual(comp, 0) hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) comp_index = 0 for ref_level, comp, data in hg3: self.assertEqual(ref_level, 0) self.assertEqual(comp, comp_index) self.assertTrue(isinstance(data, gd.UniformGridData)) comp_index += 1 # Test from finest geom = gd.UniformGrid( [81, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=0 ) geom2 = gd.UniformGrid( [11, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=1 ) sin_wave1 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom ) sin_wave2 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom2 ) sin_wave = gd.HierarchicalGridData([sin_wave1] + [sin_wave2]) index = 1 for ref_level, comp, data in sin_wave.iter_from_finest(): self.assertEqual(ref_level, index) self.assertEqual(comp, 0) self.assertTrue(isinstance(data, gd.UniformGridData)) index -= 1
def test__eq__(self): hg1 = gd.HierarchicalGridData(self.grid_data) hg2 = gd.HierarchicalGridData([self.expected_data_level2]) hg3 = gd.HierarchicalGridData([self.expected_data]) self.assertNotEqual(hg1, hg2) self.assertEqual(hg1, hg3) # Not same type self.assertNotEqual(hg1, 2) hg4 = gd.HierarchicalGridData( [self.expected_data, self.expected_data_level2] ) # Not same number of refinement levels self.assertNotEqual(hg1, hg4) # Multiple components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) self.assertEqual(hg3, hg3)
def test_partial_derivated(self): # Here we are also testing _call_component_method geom = gd.UniformGrid( [8001, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=0 ) geom2 = gd.UniformGrid( [10001, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=1 ) sin_wave1 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom ) sin_wave2 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom2 ) original_sin1 = sin_wave1.copy() original_sin2 = sin_wave2.copy() sin_wave = gd.HierarchicalGridData([sin_wave1] + [sin_wave2]) sin_copy = sin_wave.copy() # Second derivative should still be a -sin sin_wave.partial_derive(0, order=2) self.assertTrue( np.allclose(-sin_wave[0][0].data, original_sin1.data, atol=1e-3) ) self.assertTrue( np.allclose(-sin_wave[1][0].data, original_sin2.data, atol=1e-3) ) # Test _call_component_method with non-string name with self.assertRaises(TypeError): sin_wave._call_component_method(sin_wave) # Test _call_component_method with non existing method with self.assertRaises(ValueError): sin_wave._call_component_method("lol") gradient = sin_copy.gradient(order=2) # Along the first direction (it's a HierarchicalGridData) partial_x = gradient[0] self.assertTrue( np.allclose(-partial_x[0][0].data, original_sin1.data, atol=1e-3) ) # First refinement_level self.assertTrue( np.allclose(-partial_x[1][0].data, original_sin2.data, atol=1e-3) )
def test__apply_unary(self): hg1 = gd.HierarchicalGridData(self.grid_data) def neg_product(x, y): return -x * (y + 2) neg_data = gdu.sample_function_from_uniformgrid( neg_product, self.expected_grid ) hg2 = gd.HierarchicalGridData([neg_data]) self.assertEqual(-hg1, hg2) # Test with multiple components hg3 = gd.HierarchicalGridData(self.grid_data_two_comp) hg4 = hg3.copy() hg4[0][0] *= -1 hg4[0][1] *= -1 self.assertEqual(-hg3, hg4)
def test_finest_coarsest_level(self): geom = gd.UniformGrid( [81, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=0 ) geom2 = gd.UniformGrid( [11, 3], x0=[0, 0], x1=[2 * np.pi, 1], ref_level=1 ) sin_wave1 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom ) sin_wave2 = gdu.sample_function_from_uniformgrid( lambda x, y: np.sin(x), geom2 ) sin_wave = gd.HierarchicalGridData([sin_wave1] + [sin_wave2]) self.assertEqual(sin_wave.finest_level, sin_wave2) self.assertEqual(sin_wave.coarsest_level, sin_wave1)
def test_get(self): # Iteration not present with self.assertRaises(KeyError): self.P[9] # Let's read iteration 0, we have two ref levels and two components data00 = self.P._read_component_as_uniform_grid_data( self.P_file, 0, 0, 0 ) data01 = self.P._read_component_as_uniform_grid_data( self.P_file, 0, 0, 1 ) data10 = self.P._read_component_as_uniform_grid_data( self.P_file, 0, 1, 0 ) data11 = self.P._read_component_as_uniform_grid_data( self.P_file, 0, 1, 1 ) expected_hgd = grid_data.HierarchicalGridData( [data00, data01, data10, data11] ) self.assertEqual(self.P[0], expected_hgd) # default self.assertIs(self.P.get_iteration(3), None) self.assertIs(self.P.get_time(3), None) self.assertEqual(self.P.get_iteration(0), self.P[0]) self.assertEqual(self.P.get_time(0.5), self.P[2]) # Test iteration self.assertEqual(next(iter(self.P)), self.P[0]) new_grid = grid_data.UniformGrid([10, 10], x0=[1, 1], x1=[2, 2]) self.assertEqual( self.P.read_on_grid(0, new_grid), expected_hgd.to_UniformGridData_from_grid(new_grid), )
def test_preprocess_plot_functions(self): # We test preprocess_plot with a function that returns the argument, so # we can check that they are what we expect def func(data, **kwargs): return data, kwargs dec_func = viz.preprocess_plot(func) # Default self.assertIs(dec_func("")[1]["axis"], plt.gca()) # Passing axis self.assertIs(dec_func("", axis=self.ax2)[1]["axis"], self.ax2) # Default self.assertIs(dec_func("")[1]["figure"], plt.gcf()) # Passing figure self.assertIs(dec_func("", figure=self.fig)[1]["figure"], self.fig) dec_func_grid = viz.preprocess_plot_grid(func) # Check data not provided with self.assertRaises(TypeError): dec_func_grid() # Data numpy array, but not of dimension 2 with self.assertRaises(ValueError): dec_func_grid(data=np.linspace(0, 1, 2)) # Data numpy array of dimension 2 self.assertTrue( np.array_equal( dec_func_grid(data=np.array([[1, 2], [3, 4]]))[0], np.array([[1, 2], [3, 4]]), ) ) # Check with UniformGridData # 2D ugd = gdu.sample_function(lambda x, y: x + y, [10, 20], [0, 1], [2, 5]) # Passing coordinates with self.assertWarns(Warning): ret = dec_func_grid( data=ugd, coordinates=ugd.coordinates_from_grid() ) self.assertTrue(np.array_equal(ret[0], ugd.data_xyz)) self.assertIs(ret[1]["coordinates"], ugd.coordinates_from_grid()) # Passing x0 and x1 but not shape with self.assertRaises(TypeError): dec_func_grid(data=ugd, x0=ugd.x0, x1=ugd.x1) # Now HierachicalGridData or resampling UniformGridData hg = gd.HierarchicalGridData([ugd]) # Shape not provided with self.assertRaises(TypeError): dec_func_grid(data=hg) # Valid (passing x0 and x1) ret2 = dec_func_grid(data=hg, shape=ugd.shape, x0=ugd.x0, x1=ugd.x1) # Check coordinates (which checks the resampling) self.assertTrue( np.allclose( ret2[1]["coordinates"][0], ugd.coordinates_from_grid()[0] ) ) # Not passing x0 and x1 ret2b = dec_func_grid(data=hg, shape=ugd.shape) self.assertTrue( np.allclose( ret2b[1]["coordinates"][0], ugd.coordinates_from_grid()[0] ) ) # We create an empty OneGridFunctionASCII and populate it with ugd cactus_ascii = cgf.OneGridFunctionASCII([], "var_name", (0, 0)) cactus_ascii.allfiles = ["file"] cactus_ascii.alldata = {"file": {0: {0: {0: ugd}}}} # Iteration not provided with self.assertRaises(TypeError): dec_func_grid(data=cactus_ascii) # Check coordinates (which checks the resampling) ret3 = dec_func_grid( data=cactus_ascii, iteration=0, shape=ugd.shape, xlabel="x" ) self.assertTrue( np.allclose( ret3[1]["coordinates"][0], ugd.coordinates_from_grid()[0] ) ) # Test xlabel and ylabel self.assertEqual(ret3[1]["xlabel"], "x") # Test with resample=True _ = dec_func_grid( data=cactus_ascii, iteration=0, shape=ugd.shape, xlabel="x", ylabel="y", resample=True, ) # Test with masked data # HierarchicalGrid hg_m = km.arcsin(gd.HierarchicalGridData([ugd])) with self.assertWarns(Warning): dec_func_grid(data=hg_m, shape=[10, 10]) ugd_m = km.arcsin(ugd) with self.assertWarns(Warning): dec_func_grid(data=ugd_m, shape=[10, 10], x0=[1, 3])
def test__getitem__(self): hg = gd.HierarchicalGridData(self.grid_data) self.assertEqual(hg[0], [self.expected_data])