def exercise_covariance(): xs = xray.structure( crystal_symmetry=crystal.symmetry( (5.01,5.01,5.47,90,90,120), "P6222"), scatterers=flex.xray_scatterer([ xray.scatterer("Si", (1/2.,1/2.,1/3.)), xray.scatterer("O", (0.197,-0.197,0.83333))])) uc = xs.unit_cell() flags = xs.scatterer_flags() for f in flags: f.set_grad_site(True) xs.set_scatterer_flags(flags) cov = flex.double((1e-8,1e-9,2e-9,3e-9,4e-9,5e-9, 2e-8,1e-9,2e-9,3e-9,4e-9, 3e-8,1e-9,2e-9,3e-9, 2e-8,1e-9,2e-9, 3e-8,1e-9, 4e-8)) param_map = xs.parameter_map() assert approx_equal(cov, covariance.extract_covariance_matrix_for_sites(flex.size_t([0,1]), cov, param_map)) cov_cart = covariance.orthogonalize_covariance_matrix(cov, uc, param_map) O = matrix.sqr(uc.orthogonalization_matrix()) for i in range(param_map.n_scatterers): cov_i = covariance.extract_covariance_matrix_for_sites(flex.size_t([i]), cov, param_map) cov_i_cart = covariance.extract_covariance_matrix_for_sites(flex.size_t([i]), cov_cart, param_map) assert approx_equal( O * matrix.sym(sym_mat3=cov_i) * O.transpose(), matrix.sym(sym_mat3=cov_i_cart).as_mat3()) for f in flags: f.set_grads(False) flags[0].set_grad_u_aniso(True) flags[0].set_use_u_aniso(True) flags[1].set_grad_u_iso(True) flags[1].set_use_u_iso(True) xs.set_scatterer_flags(flags) param_map = xs.parameter_map() cov = flex.double(7*7, 0) cov.reshape(flex.grid(7,7)) cov.matrix_diagonal_set_in_place(flex.double([i for i in range(7)])) cov = cov.matrix_symmetric_as_packed_u() assert approx_equal([i for i in range(6)], covariance.extract_covariance_matrix_for_u_aniso( 0, cov, param_map).matrix_packed_u_diagonal()) assert covariance.variance_for_u_iso(1, cov, param_map) == 6 try: covariance.variance_for_u_iso(0, cov, param_map) except RuntimeError: pass else: raise Exception_expected try: covariance.extract_covariance_matrix_for_u_aniso(1, cov, param_map) except RuntimeError: pass else: raise Exception_expected approx_equal(covariance.extract_covariance_matrix_for_sites( flex.size_t([1]), cov, param_map), (0,0,0,0,0,0))
def exercise_covariance(): xs = xray.structure(crystal_symmetry=crystal.symmetry( (5.01, 5.01, 5.47, 90, 90, 120), "P6222"), scatterers=flex.xray_scatterer([ xray.scatterer("Si", (1 / 2., 1 / 2., 1 / 3.)), xray.scatterer("O", (0.197, -0.197, 0.83333)) ])) uc = xs.unit_cell() flags = xs.scatterer_flags() for f in flags: f.set_grad_site(True) xs.set_scatterer_flags(flags) cov = flex.double( (1e-8, 1e-9, 2e-9, 3e-9, 4e-9, 5e-9, 2e-8, 1e-9, 2e-9, 3e-9, 4e-9, 3e-8, 1e-9, 2e-9, 3e-9, 2e-8, 1e-9, 2e-9, 3e-8, 1e-9, 4e-8)) param_map = xs.parameter_map() assert approx_equal( cov, covariance.extract_covariance_matrix_for_sites(flex.size_t([0, 1]), cov, param_map)) cov_cart = covariance.orthogonalize_covariance_matrix(cov, uc, param_map) O = matrix.sqr(uc.orthogonalization_matrix()) for i in range(param_map.n_scatterers): cov_i = covariance.extract_covariance_matrix_for_sites( flex.size_t([i]), cov, param_map) cov_i_cart = covariance.extract_covariance_matrix_for_sites( flex.size_t([i]), cov_cart, param_map) assert approx_equal(O * matrix.sym(sym_mat3=cov_i) * O.transpose(), matrix.sym(sym_mat3=cov_i_cart).as_mat3()) for f in flags: f.set_grads(False) flags[0].set_grad_u_aniso(True) flags[0].set_use_u_aniso(True) flags[1].set_grad_u_iso(True) flags[1].set_use_u_iso(True) xs.set_scatterer_flags(flags) param_map = xs.parameter_map() cov = flex.double(7 * 7, 0) cov.reshape(flex.grid(7, 7)) cov.matrix_diagonal_set_in_place(flex.double([i for i in range(7)])) cov = cov.matrix_symmetric_as_packed_u() assert approx_equal([i for i in range(6)], covariance.extract_covariance_matrix_for_u_aniso( 0, cov, param_map).matrix_packed_u_diagonal()) assert covariance.variance_for_u_iso(1, cov, param_map) == 6 try: covariance.variance_for_u_iso(0, cov, param_map) except RuntimeError: pass else: raise Exception_expected try: covariance.extract_covariance_matrix_for_u_aniso(1, cov, param_map) except RuntimeError: pass else: raise Exception_expected approx_equal( covariance.extract_covariance_matrix_for_sites(flex.size_t([1]), cov, param_map), (0, 0, 0, 0, 0, 0))
def __init__(self, xray_structure, covariance_matrix=None, cell_covariance_matrix=None): crystal_symmetry_as_cif_block.__init__( self, xray_structure.crystal_symmetry(), cell_covariance_matrix=cell_covariance_matrix) scatterers = xray_structure.scatterers() uc = xray_structure.unit_cell() if covariance_matrix is not None: param_map = xray_structure.parameter_map() covariance_diagonal = covariance_matrix.matrix_packed_u_diagonal() u_star_to_u_cif_linear_map_pow2 = flex.pow2( flex.double(uc.u_star_to_u_cif_linear_map())) u_star_to_u_iso_linear_form = matrix.row( uc.u_star_to_u_iso_linear_form()) fmt = "%.6f" # _atom_site_* loop atom_site_loop = model.loop( header=('_atom_site_label', '_atom_site_type_symbol', '_atom_site_fract_x', '_atom_site_fract_y', '_atom_site_fract_z', '_atom_site_U_iso_or_equiv', '_atom_site_adp_type', '_atom_site_occupancy')) for i_seq, sc in enumerate(scatterers): # site if covariance_matrix is not None and sc.flags.grad_site(): site = [] for i in range(3): idx = param_map[i_seq].site if idx > -1: var = covariance_diagonal[idx + i] else: var = 0 if var > 0: site.append( format_float_with_su(sc.site[i], math.sqrt(var))) else: site.append(fmt % sc.site[i]) else: site = [fmt % sc.site[i] for i in range(3)] # u_eq if (covariance_matrix is not None and (sc.flags.grad_u_iso() or sc.flags.grad_u_aniso())): if sc.flags.grad_u_iso(): u_iso_or_equiv = format_float_with_su( sc.u_iso, math.sqrt( covariance.variance_for_u_iso( i_seq, covariance_matrix, param_map))) else: cov = covariance.extract_covariance_matrix_for_u_aniso( i_seq, covariance_matrix, param_map).matrix_packed_u_as_symmetric() var = (u_star_to_u_iso_linear_form * matrix.sqr(cov)).dot(u_star_to_u_iso_linear_form) u_iso_or_equiv = format_float_with_su( sc.u_iso_or_equiv(uc), math.sqrt(var)) else: u_iso_or_equiv = fmt % sc.u_iso_or_equiv(uc) if sc.flags.use_u_aniso(): adp_type = 'Uani' else: adp_type = 'Uiso' atom_site_loop.add_row( (sc.label, sc.scattering_type, site[0], site[1], site[2], u_iso_or_equiv, adp_type, fmt % sc.occupancy)) self.cif_block.add_loop(atom_site_loop) # _atom_site_aniso_* loop aniso_scatterers = scatterers.select(scatterers.extract_use_u_aniso()) if aniso_scatterers.size(): labels = list(scatterers.extract_labels()) aniso_loop = model.loop( header=('_atom_site_aniso_label', '_atom_site_aniso_U_11', '_atom_site_aniso_U_22', '_atom_site_aniso_U_33', '_atom_site_aniso_U_12', '_atom_site_aniso_U_13', '_atom_site_aniso_U_23')) for sc in aniso_scatterers: u_cif = adptbx.u_star_as_u_cif(uc, sc.u_star) if covariance_matrix is not None: row = [sc.label] idx = param_map[labels.index(sc.label)].u_aniso if idx > -1: var = covariance_diagonal[ idx:idx + 6] * u_star_to_u_cif_linear_map_pow2 for i in range(6): if var[i] > 0: row.append( format_float_with_su( u_cif[i], math.sqrt(var[i]))) else: row.append(fmt % u_cif[i]) else: row = [sc.label] + [fmt % u_cif[i] for i in range(6)] else: row = [sc.label] + [fmt % u_cif[i] for i in range(6)] aniso_loop.add_row(row) self.cif_block.add_loop(aniso_loop) self.cif_block.add_loop(atom_type_cif_loop(xray_structure))
def __init__(self, xray_structure, covariance_matrix=None, cell_covariance_matrix=None): crystal_symmetry_as_cif_block.__init__( self, xray_structure.crystal_symmetry(), cell_covariance_matrix=cell_covariance_matrix ) scatterers = xray_structure.scatterers() uc = xray_structure.unit_cell() if covariance_matrix is not None: param_map = xray_structure.parameter_map() covariance_diagonal = covariance_matrix.matrix_packed_u_diagonal() u_star_to_u_cif_linear_map_pow2 = flex.pow2(flex.double(uc.u_star_to_u_cif_linear_map())) u_star_to_u_iso_linear_form = matrix.row(uc.u_star_to_u_iso_linear_form()) fmt = "%.6f" # _atom_site_* loop atom_site_loop = model.loop( header=( "_atom_site_label", "_atom_site_type_symbol", "_atom_site_fract_x", "_atom_site_fract_y", "_atom_site_fract_z", "_atom_site_U_iso_or_equiv", "_atom_site_adp_type", "_atom_site_occupancy", ) ) for i_seq, sc in enumerate(scatterers): site = occu = u_iso_or_equiv = None # site if covariance_matrix is not None: params = param_map[i_seq] if sc.flags.grad_site() and params.site >= 0: site = [] for i in range(3): site.append(format_float_with_su(sc.site[i], math.sqrt(covariance_diagonal[params.site + i]))) # occupancy if sc.flags.grad_occupancy() and params.occupancy >= 0: occu = format_float_with_su(sc.occupancy, math.sqrt(covariance_diagonal[params.occupancy])) # Uiso/eq if sc.flags.grad_u_iso() or sc.flags.grad_u_aniso(): if sc.flags.grad_u_iso(): u_iso_or_equiv = format_float_with_su( sc.u_iso, math.sqrt(covariance.variance_for_u_iso(i_seq, covariance_matrix, param_map)) ) else: cov = covariance.extract_covariance_matrix_for_u_aniso( i_seq, covariance_matrix, param_map ).matrix_packed_u_as_symmetric() var = (u_star_to_u_iso_linear_form * matrix.sqr(cov)).dot(u_star_to_u_iso_linear_form) u_iso_or_equiv = format_float_with_su(sc.u_iso_or_equiv(uc), math.sqrt(var)) if site is None: site = [fmt % sc.site[i] for i in range(3)] if occu is None: occu = fmt % sc.occupancy if u_iso_or_equiv is None: u_iso_or_equiv = fmt % sc.u_iso_or_equiv(uc) if sc.flags.use_u_aniso(): adp_type = "Uani" else: adp_type = "Uiso" atom_site_loop.add_row( (sc.label, sc.scattering_type, site[0], site[1], site[2], u_iso_or_equiv, adp_type, occu) ) self.cif_block.add_loop(atom_site_loop) # _atom_site_aniso_* loop aniso_scatterers = scatterers.select(scatterers.extract_use_u_aniso()) if aniso_scatterers.size(): labels = list(scatterers.extract_labels()) aniso_loop = model.loop( header=( "_atom_site_aniso_label", "_atom_site_aniso_U_11", "_atom_site_aniso_U_22", "_atom_site_aniso_U_33", "_atom_site_aniso_U_12", "_atom_site_aniso_U_13", "_atom_site_aniso_U_23", ) ) for sc in aniso_scatterers: u_cif = adptbx.u_star_as_u_cif(uc, sc.u_star) if covariance_matrix is not None: row = [sc.label] idx = param_map[labels.index(sc.label)].u_aniso if idx > -1: var = covariance_diagonal[idx : idx + 6] * u_star_to_u_cif_linear_map_pow2 for i in range(6): if var[i] > 0: row.append(format_float_with_su(u_cif[i], math.sqrt(var[i]))) else: row.append(fmt % u_cif[i]) else: row = [sc.label] + [fmt % u_cif[i] for i in range(6)] else: row = [sc.label] + [fmt % u_cif[i] for i in range(6)] aniso_loop.add_row(row) self.cif_block.add_loop(aniso_loop) self.cif_block.add_loop(atom_type_cif_loop(xray_structure))