Commit a68e0534 by Maarten L. Hekkelman

Remove tests

parent 25a90e3b
data_HEM
#
_chem_comp.id HEM
_chem_comp.name "PROTOPORPHYRIN IX CONTAINING FE"
_chem_comp.type NON-POLYMER
_chem_comp.pdbx_type HETAIN
_chem_comp.formula "C34 H32 Fe N4 O4"
_chem_comp.mon_nstd_parent_comp_id ?
_chem_comp.pdbx_synonyms HEME
_chem_comp.pdbx_formal_charge 0
_chem_comp.pdbx_initial_date 1999-07-08
_chem_comp.pdbx_modified_date 2020-06-17
_chem_comp.pdbx_ambiguous_flag Y
_chem_comp.pdbx_release_status REL
_chem_comp.pdbx_replaced_by ?
_chem_comp.pdbx_replaces MHM
_chem_comp.formula_weight 616.487
_chem_comp.one_letter_code ?
_chem_comp.three_letter_code HEM
_chem_comp.pdbx_model_coordinates_details ?
_chem_comp.pdbx_model_coordinates_missing_flag N
_chem_comp.pdbx_ideal_coordinates_details Corina
_chem_comp.pdbx_ideal_coordinates_missing_flag N
_chem_comp.pdbx_model_coordinates_db_code 3IA3
_chem_comp.pdbx_subcomponent_list ?
_chem_comp.pdbx_processing_site RCSB
# #
loop_
_chem_comp_atom.comp_id
_chem_comp_atom.atom_id
_chem_comp_atom.alt_atom_id
_chem_comp_atom.type_symbol
_chem_comp_atom.charge
_chem_comp_atom.pdbx_align
_chem_comp_atom.pdbx_aromatic_flag
_chem_comp_atom.pdbx_leaving_atom_flag
_chem_comp_atom.pdbx_stereo_config
_chem_comp_atom.model_Cartn_x
_chem_comp_atom.model_Cartn_y
_chem_comp_atom.model_Cartn_z
_chem_comp_atom.pdbx_model_Cartn_x_ideal
_chem_comp_atom.pdbx_model_Cartn_y_ideal
_chem_comp_atom.pdbx_model_Cartn_z_ideal
_chem_comp_atom.pdbx_component_atom_id
_chem_comp_atom.pdbx_component_comp_id
_chem_comp_atom.pdbx_ordinal
HEM CHA CHA C 0 1 N N N 2.748 -19.531 39.896 -2.161 -0.125 0.490 CHA HEM 1
HEM CHB CHB C 0 1 N N N 3.258 -17.744 35.477 1.458 -3.419 0.306 CHB HEM 2
HEM CHC CHC C 0 1 N N N 1.703 -21.900 33.637 4.701 0.169 -0.069 CHC HEM 3
HEM CHD CHD C 0 1 N N N 1.149 -23.677 38.059 1.075 3.460 0.018 CHD HEM 4
HEM C1A C1A C 0 1 Y N N 3.031 -18.673 38.872 -1.436 -1.305 0.380 C1A HEM 5
HEM C2A C2A C 0 1 Y N N 3.578 -17.325 39.013 -2.015 -2.587 0.320 C2A HEM 6
HEM C3A C3A C 0 1 Y N N 3.705 -16.820 37.785 -1.009 -3.500 0.270 C3A HEM 7
HEM C4A C4A C 0 1 Y N N 3.256 -17.863 36.862 0.216 -2.803 0.298 C4A HEM 8
HEM CMA CMA C 0 1 N N N 4.227 -15.469 37.393 -1.175 -4.996 0.197 CMA HEM 9
HEM CAA CAA C 0 1 N N N 3.945 -16.670 40.296 -3.490 -2.893 0.314 CAA HEM 10
HEM CBA CBA C 0 1 N N N 5.391 -17.138 40.581 -3.998 -2.926 -1.129 CBA HEM 11
HEM CGA CGA C 0 1 N N N 6.095 -16.663 41.825 -5.473 -3.232 -1.136 CGA HEM 12
HEM O1A O1A O 0 1 N N N 7.098 -15.928 41.683 -6.059 -3.405 -0.094 O1A HEM 13
HEM O2A O2A O 0 1 N N N 5.657 -17.040 42.940 -6.137 -3.311 -2.300 O2A HEM 14
HEM C1B C1B C 0 1 N N N 2.888 -18.698 34.579 2.664 -2.707 0.308 C1B HEM 15
HEM C2B C2B C 0 1 N N N 2.933 -18.535 33.146 3.937 -3.328 0.418 C2B HEM 16
HEM C3B C3B C 0 1 N N N 2.499 -19.716 32.632 4.874 -2.341 0.314 C3B HEM 17
HEM C4B C4B C 0 1 N N N 2.187 -20.580 33.743 4.117 -1.079 0.139 C4B HEM 18
HEM CMB CMB C 0 1 N N N 3.391 -17.290 32.422 4.203 -4.798 0.613 CMB HEM 19
HEM CAB CAB C 0 1 N N N 2.345 -20.140 31.217 6.339 -2.497 0.365 CAB HEM 20
HEM CBB CBB C 0 1 N N N 1.755 -19.492 30.233 6.935 -3.419 -0.385 CBB HEM 21
HEM C1C C1C C 0 1 Y N N 1.395 -22.786 34.659 3.964 1.345 -0.174 C1C HEM 22
HEM C2C C2C C 0 1 Y N N 0.854 -24.130 34.500 4.531 2.601 -0.445 C2C HEM 23
HEM C3C C3C C 0 1 Y N N 0.689 -24.626 35.757 3.510 3.536 -0.437 C3C HEM 24
HEM C4C C4C C 0 1 Y N N 1.139 -23.583 36.674 2.304 2.846 -0.139 C4C HEM 25
HEM CMC CMC C 0 1 N N N 0.550 -24.782 33.175 5.991 2.880 -0.697 CMC HEM 26
HEM CAC CAC C 0 1 N N N 0.164 -25.943 36.196 3.649 4.981 -0.692 CAC HEM 27
HEM CBC CBC C 0 1 N N N 0.498 -27.158 35.750 4.201 5.407 -1.823 CBC HEM 28
HEM C1D C1D C 0 1 N N N 1.550 -22.718 38.980 -0.102 2.753 0.298 C1D HEM 29
HEM C2D C2D C 0 1 N N N 1.513 -22.879 40.415 -1.382 3.388 0.641 C2D HEM 30
HEM C3D C3D C 0 1 N N N 1.951 -21.691 40.929 -2.283 2.389 0.774 C3D HEM 31
HEM C4D C4D C 0 1 N N N 2.277 -20.826 39.811 -1.561 1.137 0.511 C4D HEM 32
HEM CMD CMD C 0 1 N N N 1.055 -24.094 41.156 -1.639 4.863 0.811 CMD HEM 33
HEM CAD CAD C 0 1 N N N 2.048 -21.326 42.352 -3.741 2.532 1.123 CAD HEM 34
HEM CBD CBD C 0 1 N N N 0.741 -20.498 42.530 -4.573 2.563 -0.160 CBD HEM 35
HEM CGD CGD C 0 1 N N N 0.578 -19.987 43.892 -6.032 2.706 0.189 CGD HEM 36
HEM O1D O1D O 0 1 N N N 1.387 -19.103 44.303 -6.372 2.776 1.347 O1D HEM 37
HEM O2D O2D O 0 1 N N N -0.401 -20.468 44.537 -6.954 2.755 -0.785 O2D HEM 38
HEM NA NA N 0 1 Y N N 2.863 -18.969 37.554 -0.068 -1.456 0.321 NA HEM 39
HEM NB NB N 0 1 N N N 2.439 -19.944 34.911 2.820 -1.386 0.207 NB HEM 40
HEM NC NC N 0 1 Y N N 1.537 -22.509 35.976 2.604 1.506 -0.033 NC HEM 41
HEM ND ND N 0 1 N N N 2.008 -21.465 38.663 -0.276 1.431 0.298 ND HEM 42
HEM FE FE FE 0 0 N N N 2.196 -20.749 36.814 1.010 0.157 -0.060 FE HEM 43
HEM HHB HHB H 0 1 N N N 3.587 -16.798 35.072 1.498 -4.508 0.309 HHB HEM 44
HEM HHC HHC H 0 1 N N N 1.553 -22.268 32.633 5.786 0.229 -0.153 HHC HEM 45
HEM HHD HHD H 0 1 N N N 0.802 -24.613 38.472 1.018 4.543 -0.083 HHD HEM 46
HEM HMA HMA H 0 1 N N N 5.316 -15.524 37.249 -1.220 -5.306 -0.847 HMA HEM 47
HEM HMAA HMAA H 0 0 N N N 3.749 -15.149 36.455 -0.328 -5.480 0.683 HMAA HEM 48
HEM HMAB HMAB H 0 0 N N N 3.998 -14.743 38.187 -2.097 -5.285 0.702 HMAB HEM 49
HEM HAA HAA H 0 1 N N N 3.905 -15.575 40.197 -3.662 -3.862 0.782 HAA HEM 50
HEM HAAA HAAA H 0 0 N N N 3.268 -16.991 41.102 -4.024 -2.121 0.869 HAAA HEM 51
HEM HBA HBA H 0 1 N N N 5.368 -18.237 40.627 -3.825 -1.956 -1.597 HBA HEM 52
HEM HBAA HBAA H 0 0 N N N 6.004 -16.819 39.725 -3.464 -3.697 -1.684 HBAA HEM 53
HEM HMB HMB H 0 1 N N N 3.319 -17.449 31.336 3.256 -5.336 0.660 HMB HEM 54
HEM HMBA HMBA H 0 0 N N N 2.753 -16.442 32.711 4.794 -5.175 -0.222 HMBA HEM 55
HEM HMBB HMBB H 0 0 N N N 4.435 -17.072 32.692 4.752 -4.948 1.543 HMBB HEM 56
HEM HAB HAB H 0 1 N N N 2.770 -21.100 30.963 6.927 -1.863 1.011 HAB HEM 57
HEM HBB HBB H 0 1 N N N 1.719 -19.927 29.245 7.994 -3.600 -0.277 HBB HEM 58
HEM HBBA HBBA H 0 0 N N N 1.308 -18.526 30.414 6.360 -3.987 -1.102 HBBA HEM 59
HEM HMC HMC H 0 1 N N N 0.153 -25.793 33.346 6.554 1.949 -0.639 HMC HEM 60
HEM HMCA HMCA H 0 0 N N N -0.196 -24.182 32.634 6.110 3.316 -1.689 HMCA HEM 61
HEM HMCB HMCB H 0 0 N N N 1.472 -24.846 32.578 6.362 3.578 0.053 HMCB HEM 62
HEM HAC HAC H 0 1 N N N -0.583 -25.916 36.975 3.303 5.694 0.042 HAC HEM 63
HEM HBC HBC H 0 1 N N N 0.027 -28.035 36.169 4.614 4.696 -2.523 HBC HEM 64
HEM HBCA HBCA H 0 0 N N N 1.239 -27.263 34.971 4.235 6.464 -2.043 HBCA HEM 65
HEM HMD HMD H 0 1 N N N 1.142 -23.919 42.238 -0.715 5.415 0.639 HMD HEM 66
HEM HMDA HMDA H 0 0 N N N 0.006 -24.304 40.902 -2.394 5.185 0.094 HMDA HEM 67
HEM HMDB HMDB H 0 0 N N N 1.680 -24.954 40.872 -1.994 5.055 1.824 HMDB HEM 68
HEM HAD HAD H 0 1 N N N 2.055 -22.216 42.999 -4.052 1.687 1.738 HAD HEM 69
HEM HADA HADA H 0 0 N N N 2.943 -20.719 42.554 -3.893 3.459 1.677 HADA HEM 70
HEM HBD HBD H 0 1 N N N 0.767 -19.646 41.835 -4.262 3.408 -0.775 HBD HEM 71
HEM HBDA HBDA H 0 0 N N N -0.119 -21.141 42.290 -4.421 1.636 -0.714 HBDA HEM 72
HEM H2A H2A H 0 1 N N N 6.201 -16.682 43.632 -7.082 -3.510 -2.254 H2A HEM 73
HEM H2D H2D H 0 1 N N N -0.445 -20.063 45.395 -7.877 2.847 -0.512 H2D HEM 74
HEM HHA HHA H 0 1 N N N 2.913 -19.150 40.893 -3.246 -0.188 0.567 HHA HEM 75
# #
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
HEM CHA C1A SING N N 1
HEM CHA C4D DOUB N N 2
HEM CHA HHA SING N N 3
HEM CHB C4A SING N N 4
HEM CHB C1B DOUB N N 5
HEM CHB HHB SING N N 6
HEM CHC C4B SING N N 7
HEM CHC C1C DOUB N N 8
HEM CHC HHC SING N N 9
HEM CHD C4C DOUB N N 10
HEM CHD C1D SING N N 11
HEM CHD HHD SING N N 12
HEM C1A C2A DOUB Y N 13
HEM C1A NA SING Y N 14
HEM C2A C3A SING Y N 15
HEM C2A CAA SING N N 16
HEM C3A C4A DOUB Y N 17
HEM C3A CMA SING N N 18
HEM C4A NA SING Y N 19
HEM CMA HMA SING N N 20
HEM CMA HMAA SING N N 21
HEM CMA HMAB SING N N 22
HEM CAA CBA SING N N 23
HEM CAA HAA SING N N 24
HEM CAA HAAA SING N N 25
HEM CBA CGA SING N N 26
HEM CBA HBA SING N N 27
HEM CBA HBAA SING N N 28
HEM CGA O1A DOUB N N 29
HEM CGA O2A SING N N 30
HEM C1B C2B SING N N 31
HEM C1B NB SING N N 32
HEM C2B C3B DOUB N N 33
HEM C2B CMB SING N N 34
HEM C3B C4B SING N N 35
HEM C3B CAB SING N N 36
HEM C4B NB DOUB N N 37
HEM CMB HMB SING N N 38
HEM CMB HMBA SING N N 39
HEM CMB HMBB SING N N 40
HEM CAB CBB DOUB N N 41
HEM CAB HAB SING N N 42
HEM CBB HBB SING N N 43
HEM CBB HBBA SING N N 44
HEM C1C C2C SING Y N 45
HEM C1C NC SING Y N 46
HEM C2C C3C DOUB Y N 47
HEM C2C CMC SING N N 48
HEM C3C C4C SING Y N 49
HEM C3C CAC SING N N 50
HEM C4C NC SING Y N 51
HEM CMC HMC SING N N 52
HEM CMC HMCA SING N N 53
HEM CMC HMCB SING N N 54
HEM CAC CBC DOUB N N 55
HEM CAC HAC SING N N 56
HEM CBC HBC SING N N 57
HEM CBC HBCA SING N N 58
HEM C1D C2D SING N N 59
HEM C1D ND DOUB N N 60
HEM C2D C3D DOUB N N 61
HEM C2D CMD SING N N 62
HEM C3D C4D SING N N 63
HEM C3D CAD SING N N 64
HEM C4D ND SING N N 65
HEM CMD HMD SING N N 66
HEM CMD HMDA SING N N 67
HEM CMD HMDB SING N N 68
HEM CAD CBD SING N N 69
HEM CAD HAD SING N N 70
HEM CAD HADA SING N N 71
HEM CBD CGD SING N N 72
HEM CBD HBD SING N N 73
HEM CBD HBDA SING N N 74
HEM CGD O1D DOUB N N 75
HEM CGD O2D SING N N 76
HEM O2A H2A SING N N 77
HEM O2D H2D SING N N 78
HEM FE NA SING N N 79
HEM FE NB SING N N 80
HEM FE NC SING N N 81
HEM FE ND SING N N 82
# #
loop_
_pdbx_chem_comp_descriptor.comp_id
_pdbx_chem_comp_descriptor.type
_pdbx_chem_comp_descriptor.program
_pdbx_chem_comp_descriptor.program_version
_pdbx_chem_comp_descriptor.descriptor
HEM SMILES ACDLabs 12.01 "C=1c3c(c(c4C=C5C(=C(C=6C=C7C(=C(C8=CC=2C(=C(C=1N=2[Fe](n34)(N5=6)N78)CCC(=O)O)C)\C=C)C)\C=C)C)C)CCC(=O)O"
HEM InChI InChI 1.03 "InChI=1S/C34H34N4O4.Fe/c1-7-21-17(3)25-13-26-19(5)23(9-11-33(39)40)31(37-26)16-32-24(10-12-34(41)42)20(6)28(38-32)15-30-22(8-2)18(4)27(36-30)14-29(21)35-25;/h7-8,13-16H,1-2,9-12H2,3-6H3,(H4,35,36,37,38,39,40,41,42);/q;+2/p-2/b25-13-,26-13-,27-14-,28-15-,29-14-,30-15-,31-16-,32-16-;"
HEM InChIKey InChI 1.03 KABFMIBPWCXCRK-RGGAHWMASA-L
HEM SMILES_CANONICAL CACTVS 3.385 "CC1=C(CCC(O)=O)C2=Cc3n4[Fe]5|6|N2=C1C=c7n5c(=CC8=N|6C(=Cc4c(C)c3CCC(O)=O)C(=C8C=C)C)c(C)c7C=C"
HEM SMILES CACTVS 3.385 "CC1=C(CCC(O)=O)C2=Cc3n4[Fe]5|6|N2=C1C=c7n5c(=CC8=N|6C(=Cc4c(C)c3CCC(O)=O)C(=C8C=C)C)c(C)c7C=C"
HEM SMILES_CANONICAL "OpenEye OEToolkits" 1.7.6 "Cc1c2n3c(c1CCC(=O)O)C=C4C(=C(C5=[N]4[Fe]36[N]7=C(C=C8N6C(=C5)C(=C8C)C=C)C(=C(C7=C2)C)C=C)C)CCC(=O)O"
HEM SMILES "OpenEye OEToolkits" 1.7.6 "Cc1c2n3c(c1CCC(=O)O)C=C4C(=C(C5=[N]4[Fe]36[N]7=C(C=C8N6C(=C5)C(=C8C)C=C)C(=C(C7=C2)C)C=C)C)CCC(=O)O"
# #
loop_
_pdbx_chem_comp_identifier.comp_id
_pdbx_chem_comp_identifier.type
_pdbx_chem_comp_identifier.program
_pdbx_chem_comp_identifier.program_version
_pdbx_chem_comp_identifier.identifier
HEM "SYSTEMATIC NAME" "OpenEye OEToolkits" 1.6.1 "3-[(5Z,10Z,14Z,19Z)-18-(2-carboxyethyl)-8,13-bis(ethenyl)-3,7,12,17-tetramethyl-21,23-dihydroporphyrin-2-yl]propanoic acid"
HEM "SYSTEMATIC NAME" ACDLabs 12.01 "[3,3'-(7,12-diethenyl-3,8,13,17-tetramethylporphyrin-2,18-diyl-kappa~4~N~21~,N~22~,N~23~,N~24~)dipropanoato(2-)]iron"
# #
loop_
_pdbx_chem_comp_audit.comp_id
_pdbx_chem_comp_audit.action_type
_pdbx_chem_comp_audit.date
_pdbx_chem_comp_audit.processing_site
HEM "Create component" 1999-07-08 RCSB
HEM "Other modification" 2016-01-20 RCSB
HEM "Modify synonyms" 2020-06-05 PDBE
#
_pdbx_chem_comp_synonyms.ordinal 1
_pdbx_chem_comp_synonyms.comp_id HEM
_pdbx_chem_comp_synonyms.name HEME
_pdbx_chem_comp_synonyms.provenance ?
_pdbx_chem_comp_synonyms.type ?
##
data_REA
#
_chem_comp.id REA
_chem_comp.name "RETINOIC ACID"
_chem_comp.type NON-POLYMER
_chem_comp.pdbx_type HETAIN
_chem_comp.formula "C20 H28 O2"
_chem_comp.mon_nstd_parent_comp_id ?
_chem_comp.pdbx_synonyms ?
_chem_comp.pdbx_formal_charge 0
_chem_comp.pdbx_initial_date 1999-07-08
_chem_comp.pdbx_modified_date 2016-10-18
_chem_comp.pdbx_ambiguous_flag N
_chem_comp.pdbx_release_status REL
_chem_comp.pdbx_replaced_by ?
_chem_comp.pdbx_replaces 3KV
_chem_comp.formula_weight 300.435
_chem_comp.one_letter_code ?
_chem_comp.three_letter_code REA
_chem_comp.pdbx_model_coordinates_details ?
_chem_comp.pdbx_model_coordinates_missing_flag N
_chem_comp.pdbx_ideal_coordinates_details Corina
_chem_comp.pdbx_ideal_coordinates_missing_flag N
_chem_comp.pdbx_model_coordinates_db_code 1CBS
_chem_comp.pdbx_subcomponent_list ?
_chem_comp.pdbx_processing_site RCSB
#
loop_
_chem_comp_atom.comp_id
_chem_comp_atom.atom_id
_chem_comp_atom.alt_atom_id
_chem_comp_atom.type_symbol
_chem_comp_atom.charge
_chem_comp_atom.pdbx_align
_chem_comp_atom.pdbx_aromatic_flag
_chem_comp_atom.pdbx_leaving_atom_flag
_chem_comp_atom.pdbx_stereo_config
_chem_comp_atom.model_Cartn_x
_chem_comp_atom.model_Cartn_y
_chem_comp_atom.model_Cartn_z
_chem_comp_atom.pdbx_model_Cartn_x_ideal
_chem_comp_atom.pdbx_model_Cartn_y_ideal
_chem_comp_atom.pdbx_model_Cartn_z_ideal
_chem_comp_atom.pdbx_component_atom_id
_chem_comp_atom.pdbx_component_comp_id
_chem_comp_atom.pdbx_ordinal
REA C1 C1 C 0 1 N N N 21.972 29.831 16.739 -4.684 0.932 -0.497 C1 REA 1
REA C2 C2 C 0 1 N N N 20.921 30.524 15.841 -5.837 0.190 -1.176 C2 REA 2
REA C3 C3 C 0 1 N N N 20.245 29.635 14.848 -6.441 -0.798 -0.171 C3 REA 3
REA C4 C4 C 0 1 N N N 19.555 28.479 15.488 -5.418 -1.903 0.100 C4 REA 4
REA C5 C5 C 0 1 N N N 20.389 27.812 16.587 -4.082 -1.301 0.429 C5 REA 5
REA C6 C6 C 0 1 N N N 21.425 28.446 17.218 -3.756 -0.048 0.161 C6 REA 6
REA C7 C7 C 0 1 N N N 22.242 27.851 18.297 -2.457 0.396 0.516 C7 REA 7
REA C8 C8 C 0 1 N N N 21.868 26.977 19.240 -1.363 -0.229 0.007 C8 REA 8
REA C9 C9 C 0 1 N N N 22.705 26.434 20.286 -0.076 0.257 0.298 C9 REA 9
REA C10 C10 C 0 1 N N N 22.159 25.536 21.131 1.022 -0.370 -0.213 C10 REA 10
REA C11 C11 C 0 1 N N N 22.875 24.924 22.234 2.306 0.115 0.077 C11 REA 11
REA C12 C12 C 0 1 N N N 22.237 24.026 22.990 3.405 -0.513 -0.435 C12 REA 12
REA C13 C13 C 0 1 N N N 22.856 23.377 24.125 4.689 -0.028 -0.144 C13 REA 13
REA C14 C14 C 0 1 N N N 22.135 22.473 24.834 5.787 -0.655 -0.656 C14 REA 14
REA C15 C15 C 0 1 N N N 22.563 21.710 26.016 7.077 -0.265 -0.244 C15 REA 15
REA C16 C16 C 0 1 N N N 22.238 30.737 17.948 -5.246 1.886 0.559 C16 REA 16
REA C17 C17 C 0 1 N N N 23.292 29.620 15.948 -3.911 1.737 -1.544 C17 REA 17
REA C18 C18 C 0 1 N N N 19.791 26.449 16.947 -3.056 -2.175 1.103 C18 REA 18
REA C19 C19 C 0 1 N N N 24.181 26.841 20.385 0.090 1.471 1.175 C19 REA 19
REA C20 C20 C 0 1 N N N 24.303 23.747 24.489 4.855 1.186 0.733 C20 REA 20
REA O1 O1 O 0 1 N N N 23.640 21.075 25.978 7.210 0.553 0.648 O1 REA 21
REA O2 O2 O 0 1 N N N 21.840 21.712 27.037 8.166 -0.798 -0.840 O2 REA 22
REA H21 H21 H 0 1 N N N 20.147 30.955 16.494 -6.598 0.905 -1.490 H21 REA 23
REA H22 H22 H 0 1 N N N 21.425 31.330 15.288 -5.462 -0.353 -2.044 H22 REA 24
REA H31 H31 H 0 1 N N N 19.501 30.227 14.295 -6.673 -0.278 0.759 H31 REA 25
REA H32 H32 H 0 1 N N N 21.001 29.250 14.148 -7.349 -1.234 -0.586 H32 REA 26
REA H41 H41 H 0 1 N N N 18.613 28.835 15.931 -5.756 -2.511 0.938 H41 REA 27
REA H42 H42 H 0 1 N N N 19.335 27.730 14.713 -5.322 -2.531 -0.786 H42 REA 28
REA H7 H7 H 0 1 N N N 23.276 28.162 18.329 -2.337 1.230 1.191 H7 REA 29
REA H8 H8 H 0 1 N N N 20.840 26.645 19.217 -1.482 -1.100 -0.622 H8 REA 30
REA H10 H10 H 0 1 N N N 21.127 25.256 20.977 0.903 -1.241 -0.842 H10 REA 31
REA H11 H11 H 0 1 N N N 23.902 25.189 22.440 2.425 0.985 0.706 H11 REA 32
REA H12 H12 H 0 1 N N N 21.216 23.774 22.743 3.286 -1.383 -1.063 H12 REA 33
REA H14 H14 H 0 1 N N N 21.127 22.292 24.490 5.667 -1.451 -1.376 H14 REA 34
REA H161 H161 H 0 0 N N N 22.984 30.265 18.604 -5.802 1.316 1.303 H161 REA 35
REA H162 H162 H 0 0 N N N 22.618 31.709 17.601 -4.426 2.415 1.044 H162 REA 36
REA H163 H163 H 0 0 N N N 21.302 30.887 18.506 -5.911 2.605 0.081 H163 REA 37
REA H171 H171 H 0 0 N N N 24.033 29.127 16.595 -4.598 2.394 -2.077 H171 REA 38
REA H172 H172 H 0 0 N N N 23.095 28.989 15.069 -3.146 2.335 -1.050 H172 REA 39
REA H173 H173 H 0 0 N N N 23.683 30.595 15.620 -3.439 1.054 -2.251 H173 REA 40
REA H181 H181 H 0 0 N N N 20.397 25.979 17.736 -3.448 -3.187 1.201 H181 REA 41
REA H182 H182 H 0 0 N N N 18.761 26.584 17.308 -2.145 -2.194 0.503 H182 REA 42
REA H183 H183 H 0 0 N N N 19.786 25.804 16.056 -2.831 -1.775 2.092 H183 REA 43
REA H191 H191 H 0 0 N N N 24.647 26.327 21.238 0.171 1.159 2.216 H191 REA 44
REA H192 H192 H 0 0 N N N 24.702 26.559 19.458 0.993 2.008 0.885 H192 REA 45
REA H193 H193 H 0 0 N N N 24.252 27.929 20.529 -0.774 2.125 1.058 H193 REA 46
REA H201 H201 H 0 0 N N N 24.620 23.168 25.369 5.026 0.871 1.762 H201 REA 47
REA H202 H202 H 0 0 N N N 24.965 23.516 23.641 5.707 1.771 0.386 H202 REA 48
REA H203 H203 H 0 0 N N N 24.360 24.822 24.717 3.952 1.795 0.685 H203 REA 49
REA HO2 HO2 H 0 1 N N N 22.244 21.180 27.713 9.006 -0.469 -0.490 HO2 REA 50
#
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
REA C1 C2 SING N N 1
REA C1 C6 SING N N 2
REA C1 C16 SING N N 3
REA C1 C17 SING N N 4
REA C2 C3 SING N N 5
REA C2 H21 SING N N 6
REA C2 H22 SING N N 7
REA C3 C4 SING N N 8
REA C3 H31 SING N N 9
REA C3 H32 SING N N 10
REA C4 C5 SING N N 11
REA C4 H41 SING N N 12
REA C4 H42 SING N N 13
REA C5 C6 DOUB N N 14
REA C5 C18 SING N N 15
REA C6 C7 SING N N 16
REA C7 C8 DOUB N E 17
REA C7 H7 SING N N 18
REA C8 C9 SING N N 19
REA C8 H8 SING N N 20
REA C9 C10 DOUB N E 21
REA C9 C19 SING N N 22
REA C10 C11 SING N N 23
REA C10 H10 SING N N 24
REA C11 C12 DOUB N E 25
REA C11 H11 SING N N 26
REA C12 C13 SING N N 27
REA C12 H12 SING N N 28
REA C13 C14 DOUB N E 29
REA C13 C20 SING N N 30
REA C14 C15 SING N N 31
REA C14 H14 SING N N 32
REA C15 O1 DOUB N N 33
REA C15 O2 SING N N 34
REA C16 H161 SING N N 35
REA C16 H162 SING N N 36
REA C16 H163 SING N N 37
REA C17 H171 SING N N 38
REA C17 H172 SING N N 39
REA C17 H173 SING N N 40
REA C18 H181 SING N N 41
REA C18 H182 SING N N 42
REA C18 H183 SING N N 43
REA C19 H191 SING N N 44
REA C19 H192 SING N N 45
REA C19 H193 SING N N 46
REA C20 H201 SING N N 47
REA C20 H202 SING N N 48
REA C20 H203 SING N N 49
REA O2 HO2 SING N N 50
#
loop_
_pdbx_chem_comp_descriptor.comp_id
_pdbx_chem_comp_descriptor.type
_pdbx_chem_comp_descriptor.program
_pdbx_chem_comp_descriptor.program_version
_pdbx_chem_comp_descriptor.descriptor
REA SMILES ACDLabs 12.01 "C1(CCCC(=C1\C=C\C(=C\C=C\C(=C\C(=O)O)C)C)C)(C)C"
REA InChI InChI 1.03 "InChI=1S/C20H28O2/c1-15(8-6-9-16(2)14-19(21)22)11-12-18-17(3)10-7-13-20(18,4)5/h6,8-9,11-12,14H,7,10,13H2,1-5H3,(H,21,22)/b9-6+,12-11+,15-8+,16-14+"
REA InChIKey InChI 1.03 SHGAZHPCJJPHSC-YCNIQYBTSA-N
REA SMILES_CANONICAL CACTVS 3.385 "CC1=C(\C=C\C(C)=C\C=C\C(C)=C\C(O)=O)C(C)(C)CCC1"
REA SMILES CACTVS 3.385 "CC1=C(C=CC(C)=CC=CC(C)=CC(O)=O)C(C)(C)CCC1"
REA SMILES_CANONICAL "OpenEye OEToolkits" 1.7.6 "CC1=C(C(CCC1)(C)C)/C=C/C(=C/C=C/C(=C/C(=O)O)/C)/C"
REA SMILES "OpenEye OEToolkits" 1.7.6 "CC1=C(C(CCC1)(C)C)C=CC(=CC=CC(=CC(=O)O)C)C"
#
loop_
_pdbx_chem_comp_identifier.comp_id
_pdbx_chem_comp_identifier.type
_pdbx_chem_comp_identifier.program
_pdbx_chem_comp_identifier.program_version
_pdbx_chem_comp_identifier.identifier
REA "SYSTEMATIC NAME" ACDLabs 12.01 "retinoic acid"
REA "SYSTEMATIC NAME" "OpenEye OEToolkits" 1.7.6 "(2E,4E,6E,8E)-3,7-dimethyl-9-(2,6,6-trimethylcyclohexen-1-yl)nona-2,4,6,8-tetraenoic acid"
#
loop_
_pdbx_chem_comp_audit.comp_id
_pdbx_chem_comp_audit.action_type
_pdbx_chem_comp_audit.date
_pdbx_chem_comp_audit.processing_site
REA "Create component" 1999-07-08 RCSB
REA "Modify descriptor" 2011-06-04 RCSB
REA "Other modification" 2016-10-18 RCSB
#
data_RXA
#
_chem_comp.id RXA
_chem_comp.name "RENAMED RETINOIC ACID"
_chem_comp.type NON-POLYMER
_chem_comp.pdbx_type HETAIN
_chem_comp.formula "C20 H28 O2"
_chem_comp.mon_nstd_parent_comp_id ?
_chem_comp.pdbx_synonyms ?
_chem_comp.pdbx_formal_charge 0
_chem_comp.pdbx_initial_date 1999-07-08
_chem_comp.pdbx_modified_date 2016-10-18
_chem_comp.pdbx_ambiguous_flag N
_chem_comp.pdbx_release_status REL
_chem_comp.pdbx_replaced_by ?
_chem_comp.pdbx_replaces 3KV
_chem_comp.formula_weight 300.435
_chem_comp.one_letter_code ?
_chem_comp.three_letter_code RXA
_chem_comp.pdbx_model_coordinates_details ?
_chem_comp.pdbx_model_coordinates_missing_flag N
_chem_comp.pdbx_ideal_coordinates_details Corina
_chem_comp.pdbx_ideal_coordinates_missing_flag N
_chem_comp.pdbx_model_coordinates_db_code 1CBS
_chem_comp.pdbx_subcomponent_list ?
_chem_comp.pdbx_processing_site RCSB
#
loop_
_chem_comp_atom.comp_id
_chem_comp_atom.atom_id
_chem_comp_atom.alt_atom_id
_chem_comp_atom.type_symbol
_chem_comp_atom.charge
_chem_comp_atom.pdbx_align
_chem_comp_atom.pdbx_aromatic_flag
_chem_comp_atom.pdbx_leaving_atom_flag
_chem_comp_atom.pdbx_stereo_config
_chem_comp_atom.model_Cartn_x
_chem_comp_atom.model_Cartn_y
_chem_comp_atom.model_Cartn_z
_chem_comp_atom.pdbx_model_Cartn_x_ideal
_chem_comp_atom.pdbx_model_Cartn_y_ideal
_chem_comp_atom.pdbx_model_Cartn_z_ideal
_chem_comp_atom.pdbx_component_atom_id
_chem_comp_atom.pdbx_component_comp_id
_chem_comp_atom.pdbx_ordinal
RXA C1 C1 C 0 1 N N N 21.972 29.831 16.739 -4.684 0.932 -0.497 C1 RXA 1
RXA C2 C2 C 0 1 N N N 20.921 30.524 15.841 -5.837 0.190 -1.176 C2 RXA 2
RXA C3 C3 C 0 1 N N N 20.245 29.635 14.848 -6.441 -0.798 -0.171 C3 RXA 3
RXA C4 C4 C 0 1 N N N 19.555 28.479 15.488 -5.418 -1.903 0.100 C4 RXA 4
RXA C5 C5 C 0 1 N N N 20.389 27.812 16.587 -4.082 -1.301 0.429 C5 RXA 5
RXA C6 C6 C 0 1 N N N 21.425 28.446 17.218 -3.756 -0.048 0.161 C6 RXA 6
RXA C7 C7 C 0 1 N N N 22.242 27.851 18.297 -2.457 0.396 0.516 C7 RXA 7
RXA C8 C8 C 0 1 N N N 21.868 26.977 19.240 -1.363 -0.229 0.007 C8 RXA 8
RXA C9 C9 C 0 1 N N N 22.705 26.434 20.286 -0.076 0.257 0.298 C9 RXA 9
RXA C10 C10 C 0 1 N N N 22.159 25.536 21.131 1.022 -0.370 -0.213 C10 RXA 10
RXA C11 C11 C 0 1 N N N 22.875 24.924 22.234 2.306 0.115 0.077 C11 RXA 11
RXA C12 C12 C 0 1 N N N 22.237 24.026 22.990 3.405 -0.513 -0.435 C12 RXA 12
RXA C13 C13 C 0 1 N N N 22.856 23.377 24.125 4.689 -0.028 -0.144 C13 RXA 13
RXA C14 C14 C 0 1 N N N 22.135 22.473 24.834 5.787 -0.655 -0.656 C14 RXA 14
RXA C15 C15 C 0 1 N N N 22.563 21.710 26.016 7.077 -0.265 -0.244 C15 RXA 15
RXA C16 C16 C 0 1 N N N 22.238 30.737 17.948 -5.246 1.886 0.559 C16 RXA 16
RXA C17 C17 C 0 1 N N N 23.292 29.620 15.948 -3.911 1.737 -1.544 C17 RXA 17
RXA C18 C18 C 0 1 N N N 19.791 26.449 16.947 -3.056 -2.175 1.103 C18 RXA 18
RXA C19 C19 C 0 1 N N N 24.181 26.841 20.385 0.090 1.471 1.175 C19 RXA 19
RXA C20 C20 C 0 1 N N N 24.303 23.747 24.489 4.855 1.186 0.733 C20 RXA 20
RXA O1 O1 O 0 1 N N N 23.640 21.075 25.978 7.210 0.553 0.648 O1 RXA 21
RXA O2 O2 O 0 1 N N N 21.840 21.712 27.037 8.166 -0.798 -0.840 O2 RXA 22
RXA H21 H21 H 0 1 N N N 20.147 30.955 16.494 -6.598 0.905 -1.490 H21 RXA 23
RXA H22 H22 H 0 1 N N N 21.425 31.330 15.288 -5.462 -0.353 -2.044 H22 RXA 24
RXA H31 H31 H 0 1 N N N 19.501 30.227 14.295 -6.673 -0.278 0.759 H31 RXA 25
RXA H32 H32 H 0 1 N N N 21.001 29.250 14.148 -7.349 -1.234 -0.586 H32 RXA 26
RXA H41 H41 H 0 1 N N N 18.613 28.835 15.931 -5.756 -2.511 0.938 H41 RXA 27
RXA H42 H42 H 0 1 N N N 19.335 27.730 14.713 -5.322 -2.531 -0.786 H42 RXA 28
RXA H7 H7 H 0 1 N N N 23.276 28.162 18.329 -2.337 1.230 1.191 H7 RXA 29
RXA H8 H8 H 0 1 N N N 20.840 26.645 19.217 -1.482 -1.100 -0.622 H8 RXA 30
RXA H10 H10 H 0 1 N N N 21.127 25.256 20.977 0.903 -1.241 -0.842 H10 RXA 31
RXA H11 H11 H 0 1 N N N 23.902 25.189 22.440 2.425 0.985 0.706 H11 RXA 32
RXA H12 H12 H 0 1 N N N 21.216 23.774 22.743 3.286 -1.383 -1.063 H12 RXA 33
RXA H14 H14 H 0 1 N N N 21.127 22.292 24.490 5.667 -1.451 -1.376 H14 RXA 34
RXA H161 H161 H 0 0 N N N 22.984 30.265 18.604 -5.802 1.316 1.303 H161 RXA 35
RXA H162 H162 H 0 0 N N N 22.618 31.709 17.601 -4.426 2.415 1.044 H162 RXA 36
RXA H163 H163 H 0 0 N N N 21.302 30.887 18.506 -5.911 2.605 0.081 H163 RXA 37
RXA H171 H171 H 0 0 N N N 24.033 29.127 16.595 -4.598 2.394 -2.077 H171 RXA 38
RXA H172 H172 H 0 0 N N N 23.095 28.989 15.069 -3.146 2.335 -1.050 H172 RXA 39
RXA H173 H173 H 0 0 N N N 23.683 30.595 15.620 -3.439 1.054 -2.251 H173 RXA 40
RXA H181 H181 H 0 0 N N N 20.397 25.979 17.736 -3.448 -3.187 1.201 H181 RXA 41
RXA H182 H182 H 0 0 N N N 18.761 26.584 17.308 -2.145 -2.194 0.503 H182 RXA 42
RXA H183 H183 H 0 0 N N N 19.786 25.804 16.056 -2.831 -1.775 2.092 H183 RXA 43
RXA H191 H191 H 0 0 N N N 24.647 26.327 21.238 0.171 1.159 2.216 H191 RXA 44
RXA H192 H192 H 0 0 N N N 24.702 26.559 19.458 0.993 2.008 0.885 H192 RXA 45
RXA H193 H193 H 0 0 N N N 24.252 27.929 20.529 -0.774 2.125 1.058 H193 RXA 46
RXA H201 H201 H 0 0 N N N 24.620 23.168 25.369 5.026 0.871 1.762 H201 RXA 47
RXA H202 H202 H 0 0 N N N 24.965 23.516 23.641 5.707 1.771 0.386 H202 RXA 48
RXA H203 H203 H 0 0 N N N 24.360 24.822 24.717 3.952 1.795 0.685 H203 RXA 49
RXA HO2 HO2 H 0 1 N N N 22.244 21.180 27.713 9.006 -0.469 -0.490 HO2 RXA 50
#
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
RXA C1 C2 SING N N 1
RXA C1 C6 SING N N 2
RXA C1 C16 SING N N 3
RXA C1 C17 SING N N 4
RXA C2 C3 SING N N 5
RXA C2 H21 SING N N 6
RXA C2 H22 SING N N 7
RXA C3 C4 SING N N 8
RXA C3 H31 SING N N 9
RXA C3 H32 SING N N 10
RXA C4 C5 SING N N 11
RXA C4 H41 SING N N 12
RXA C4 H42 SING N N 13
RXA C5 C6 DOUB N N 14
RXA C5 C18 SING N N 15
RXA C6 C7 SING N N 16
RXA C7 C8 DOUB N E 17
RXA C7 H7 SING N N 18
RXA C8 C9 SING N N 19
RXA C8 H8 SING N N 20
RXA C9 C10 DOUB N E 21
RXA C9 C19 SING N N 22
RXA C10 C11 SING N N 23
RXA C10 H10 SING N N 24
RXA C11 C12 DOUB N E 25
RXA C11 H11 SING N N 26
RXA C12 C13 SING N N 27
RXA C12 H12 SING N N 28
RXA C13 C14 DOUB N E 29
RXA C13 C20 SING N N 30
RXA C14 C15 SING N N 31
RXA C14 H14 SING N N 32
RXA C15 O1 DOUB N N 33
RXA C15 O2 SING N N 34
RXA C16 H161 SING N N 35
RXA C16 H162 SING N N 36
RXA C16 H163 SING N N 37
RXA C17 H171 SING N N 38
RXA C17 H172 SING N N 39
RXA C17 H173 SING N N 40
RXA C18 H181 SING N N 41
RXA C18 H182 SING N N 42
RXA C18 H183 SING N N 43
RXA C19 H191 SING N N 44
RXA C19 H192 SING N N 45
RXA C19 H193 SING N N 46
RXA C20 H201 SING N N 47
RXA C20 H202 SING N N 48
RXA C20 H203 SING N N 49
RXA O2 HO2 SING N N 50
#
loop_
_pdbx_chem_comp_descriptor.comp_id
_pdbx_chem_comp_descriptor.type
_pdbx_chem_comp_descriptor.program
_pdbx_chem_comp_descriptor.program_version
_pdbx_chem_comp_descriptor.descriptor
RXA SMILES ACDLabs 12.01 "C1(CCCC(=C1\C=C\C(=C\C=C\C(=C\C(=O)O)C)C)C)(C)C"
RXA InChI InChI 1.03 "InChI=1S/C20H28O2/c1-15(8-6-9-16(2)14-19(21)22)11-12-18-17(3)10-7-13-20(18,4)5/h6,8-9,11-12,14H,7,10,13H2,1-5H3,(H,21,22)/b9-6+,12-11+,15-8+,16-14+"
RXA InChIKey InChI 1.03 SHGAZHPCJJPHSC-YCNIQYBTSA-N
RXA SMILES_CANONICAL CACTVS 3.385 "CC1=C(\C=C\C(C)=C\C=C\C(C)=C\C(O)=O)C(C)(C)CCC1"
RXA SMILES CACTVS 3.385 "CC1=C(C=CC(C)=CC=CC(C)=CC(O)=O)C(C)(C)CCC1"
RXA SMILES_CANONICAL "OpenEye OEToolkits" 1.7.6 "CC1=C(C(CCC1)(C)C)/C=C/C(=C/C=C/C(=C/C(=O)O)/C)/C"
RXA SMILES "OpenEye OEToolkits" 1.7.6 "CC1=C(C(CCC1)(C)C)C=CC(=CC=CC(=CC(=O)O)C)C"
#
loop_
_pdbx_chem_comp_identifier.comp_id
_pdbx_chem_comp_identifier.type
_pdbx_chem_comp_identifier.program
_pdbx_chem_comp_identifier.program_version
_pdbx_chem_comp_identifier.identifier
RXA "SYSTEMATIC NAME" ACDLabs 12.01 "retinoic acid"
RXA "SYSTEMATIC NAME" "OpenEye OEToolkits" 1.7.6 "(2E,4E,6E,8E)-3,7-dimethyl-9-(2,6,6-trimethylcyclohexen-1-yl)nona-2,4,6,8-tetraenoic acid"
#
loop_
_pdbx_chem_comp_audit.comp_id
_pdbx_chem_comp_audit.action_type
_pdbx_chem_comp_audit.date
_pdbx_chem_comp_audit.processing_site
RXA "Create component" 1999-07-08 RCSB
RXA "Modify descriptor" 2011-06-04 RCSB
RXA "Other modification" 2016-10-18 RCSB
#
#
data_comp_list
loop_
_chem_comp.id
_chem_comp.three_letter_code
_chem_comp.name
_chem_comp.group
_chem_comp.number_atoms_all
_chem_comp.number_atoms_nh
_chem_comp.desc_level
UN_ UN_ UN_NINE L-peptide 13 6 .
#
data_comp_UN_
#
loop_
_chem_comp_atom.comp_id
_chem_comp_atom.atom_id
_chem_comp_atom.type_symbol
_chem_comp_atom.type_energy
_chem_comp_atom.charge
_chem_comp_atom.x
_chem_comp_atom.y
_chem_comp_atom.z
UN_ N N NT3 1 0.227 -1.259 0.452
UN_ H H H 0 0.069 -1.019 1.421
UN_ H2 H H 0 1.104 -1.640 0.356
UN_ H3 H H 0 -0.424 -1.909 0.174
UN_ CA C CH1 0 0.103 -0.030 -0.392
UN_ HA H H 0 0.160 -0.299 -1.339
UN_ CB C CH3 0 -1.244 0.625 -0.159
UN_ HB3 H H 0 -1.857 -0.018 0.234
UN_ HB2 H H 0 -1.605 0.932 -1.008
UN_ HB1 H H 0 -1.150 1.385 0.442
UN_ C C C 0 1.270 0.922 -0.094
UN_ O O O 0 2.008 1.323 -0.994
UN_ OXT O OC -1 1.498 1.305 1.054
loop_
_chem_comp_tree.comp_id
_chem_comp_tree.atom_id
_chem_comp_tree.atom_back
_chem_comp_tree.atom_forward
_chem_comp_tree.connect_type
UN_ N n/a CA START
UN_ H N . .
UN_ H2 N . .
UN_ H3 N . .
UN_ CA N C .
UN_ HA CA . .
UN_ CB CA HB3 .
UN_ HB1 CB . .
UN_ HB2 CB . .
UN_ HB3 CB . .
UN_ C CA . END
UN_ O C . .
UN_ OXT C . .
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.type
_chem_comp_bond.aromatic
_chem_comp_bond.value_dist
_chem_comp_bond.value_dist_esd
UN_ CB CA SINGLE n 1.509 0.014
UN_ CA C SINGLE n 1.533 0.011
UN_ C O DOUBLE n 1.247 0.019
UN_ C OXT SINGLE n 1.247 0.019
UN_ CA N SINGLE n 1.482 0.010
UN_ CB HB3 SINGLE n 0.972 0.015
UN_ CB HB2 SINGLE n 0.972 0.015
UN_ CB HB1 SINGLE n 0.972 0.015
UN_ CA HA SINGLE n 0.986 0.020
UN_ N H SINGLE n 0.911 0.020
UN_ N H2 SINGLE n 0.911 0.020
UN_ N H3 SINGLE n 0.911 0.020
loop_
_chem_comp_angle.comp_id
_chem_comp_angle.atom_id_1
_chem_comp_angle.atom_id_2
_chem_comp_angle.atom_id_3
_chem_comp_angle.value_angle
_chem_comp_angle.value_angle_esd
UN_ CA CB HB3 109.546 1.50
UN_ CA CB HB2 109.546 1.50
UN_ CA CB HB1 109.546 1.50
UN_ HB3 CB HB2 109.386 1.50
UN_ HB3 CB HB1 109.386 1.50
UN_ HB2 CB HB1 109.386 1.50
UN_ CB CA C 111.490 1.50
UN_ CB CA N 109.912 1.50
UN_ CB CA HA 108.878 1.50
UN_ C CA N 109.627 1.50
UN_ C CA HA 108.541 1.50
UN_ N CA HA 108.529 1.50
UN_ CA C O 117.159 1.57
UN_ CA C OXT 117.159 1.57
UN_ O C OXT 125.683 1.50
UN_ CA N H 109.643 1.50
UN_ CA N H2 109.643 1.50
UN_ CA N H3 109.643 1.50
UN_ H N H2 109.028 2.41
UN_ H N H3 109.028 2.41
UN_ H2 N H3 109.028 2.41
loop_
_chem_comp_tor.comp_id
_chem_comp_tor.id
_chem_comp_tor.atom_id_1
_chem_comp_tor.atom_id_2
_chem_comp_tor.atom_id_3
_chem_comp_tor.atom_id_4
_chem_comp_tor.value_angle
_chem_comp_tor.value_angle_esd
_chem_comp_tor.period
UN_ hh1 N CA CB HB3 60.000 15.000 3
UN_ sp2_sp3_1 O C CA CB 0.000 10.00 6
UN_ sp3_sp3_10 CB CA N H 180.000 10.00 3
loop_
_chem_comp_chir.comp_id
_chem_comp_chir.id
_chem_comp_chir.atom_id_centre
_chem_comp_chir.atom_id_1
_chem_comp_chir.atom_id_2
_chem_comp_chir.atom_id_3
_chem_comp_chir.volume_sign
UN_ chir_1 CA N C CB positive
loop_
_chem_comp_plane_atom.comp_id
_chem_comp_plane_atom.plane_id
_chem_comp_plane_atom.atom_id
_chem_comp_plane_atom.dist_esd
UN_ plan-1 C 0.020
UN_ plan-1 CA 0.020
UN_ plan-1 O 0.020
UN_ plan-1 OXT 0.020
loop_
_pdbx_chem_comp_descriptor.comp_id
_pdbx_chem_comp_descriptor.type
_pdbx_chem_comp_descriptor.program
_pdbx_chem_comp_descriptor.program_version
_pdbx_chem_comp_descriptor.descriptor
UN_ SMILES ACDLabs 10.04 "O=C(O)C(N)C"
UN_ SMILES_CANONICAL CACTVS 3.341 "C[C@H](N)C(O)=O"
UN_ SMILES CACTVS 3.341 "C[CH](N)C(O)=O"
UN_ SMILES_CANONICAL "OpenEye OEToolkits" 1.5.0 "C[C@@H](C(=O)O)N"
UN_ SMILES "OpenEye OEToolkits" 1.5.0 "CC(C(=O)O)N"
UN_ InChI InChI 1.03 "InChI=1S/C3H7NO2/c1-2(4)3(5)6/h2H,4H2,1H3,(H,5,6)/t2-/m0/s1"
UN_ InChIKey InChI 1.03 QNAYBMKLOCPYGJ-REOHCLBHSA-N
UN_ ? acedrg 195 "dictionary generator"
UN_ ? acedrg_database 11 "data source"
UN_ ? rdkit 2017.03.2 "Chemoinformatics tool"
UN_ ? refmac5 5.8.0189 "optimization tool"
#include "../include/cif++/cif.hpp"
#include "../include/cif++/pdb/PDB2Cif.hpp""
#include <iostream>
#include <fstream>
// #include "pdb2cif.h"
int main(int argc, char* argv[])
{
using namespace std::literals;
if (argc != 2)
{
std::cerr << "Usage: pdb2cif-test <input-file>" << std::endl;
exit(1);
}
std::ifstream is(argv[1]);
if (not is.is_open())
throw std::runtime_error("Could not open file "s + argv[1]);
cif::File f;
ReadPDBFile(is, f);
f.save(std::cout);
return 0;
}
#include "../include/cif++/Cif++.hpp"
#include "../include/cif++/PDB2Cif.hpp"
#include "../include/cif++/Structure.hpp"
#include <iostream>
#include <fstream>
int main(int argc, char* argv[])
{
cif::VERBOSE = 3;
try
{
std::filesystem::path testdir = std::filesystem::current_path();
if (argc == 3)
testdir = argv[2];
if (std::filesystem::exists(testdir / ".." / "data" / "ccd-subset.cif"))
cif::add_file_resource("components.cif", testdir / ".." / "data" / "ccd-subset.cif");
if (std::filesystem::exists(testdir / ".." / "rsrc" / "mmcif_pdbx.dic"))
cif::add_file_resource("mmcif_pdbx.dic", testdir / ".." / "rsrc" / "mmcif_pdbx.dic");
mmcif::CompoundFactory::instance().pushDictionary(testdir / "REA.cif");
mmcif::CompoundFactory::instance().pushDictionary(testdir / "RXA.cif");
mmcif::File f(testdir / ".."/"examples"/"1cbs.cif.gz");
mmcif::Structure structure(f);
auto &res = structure.getResidue("B");
structure.changeResidue(res, "RXA", {});
structure.cleanupEmptyCategories();
f.save(std::cout);
}
catch (const std::exception& e)
{
std::cerr << e.what() << std::endl;
exit(1);
}
return 0;
}
/*-
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (c) 2021 NKI/AVL, Netherlands Cancer Institute
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#define BOOST_TEST_ALTERNATIVE_INIT_API
#include <boost/test/included/unit_test.hpp>
#include <stdexcept>
#include <cif++.hpp>
#include <cif++/structure/Structure.hpp>
// --------------------------------------------------------------------
cif::File operator""_cf(const char* text, size_t length)
{
struct membuf : public std::streambuf
{
membuf(char* text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char*>(text), length);
std::istream is(&buffer);
return cif::File(is);
}
// --------------------------------------------------------------------
std::filesystem::path gTestDir = std::filesystem::current_path();
bool init_unit_test()
{
cif::VERBOSE = 1;
// not a test, just initialize test dir
if (boost::unit_test::framework::master_test_suite().argc == 2)
gTestDir = boost::unit_test::framework::master_test_suite().argv[1];
// do this now, avoids the need for installing
cif::add_file_resource("mmcif_pdbx.dic", gTestDir / ".." / "rsrc" / "mmcif_pdbx.dic");
// initialize CCD location
cif::add_file_resource("components.cif", gTestDir / ".." / "data" / "ccd-subset.cif");
mmcif::CompoundFactory::instance().pushDictionary(gTestDir / "HEM.cif");
return true;
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(create_nonpoly_1)
{
cif::VERBOSE = 1;
mmcif::File file;
file.loadDictionary("mmcif_pdbx.dic");
file.emplace("TEST"); // create a datablock
mmcif::Structure structure(file);
std::string entity_id = structure.createNonPolyEntity("HEM");
auto atoms = R"(
data_HEM
loop_
_atom_site.group_PDB
_atom_site.type_symbol
_atom_site.label_atom_id
_atom_site.label_alt_id
_atom_site.pdbx_PDB_ins_code
_atom_site.Cartn_x
_atom_site.Cartn_y
_atom_site.Cartn_z
_atom_site.occupancy
_atom_site.B_iso_or_equiv
_atom_site.pdbx_formal_charge
HETATM C CHA . ? -5.248 39.769 -0.250 1.00 7.67 ?
HETATM C CHB . ? -3.774 36.790 3.280 1.00 7.05 ?
HETATM C CHC . ? -2.879 33.328 0.013 1.00 7.69 ?
HETATM C CHD . ? -4.342 36.262 -3.536 1.00 8.00 ?
# that's enough to test with
)"_cf;
auto &hem_data = atoms["HEM"];
auto &atom_site = hem_data["atom_site"];
auto hem_atoms = atom_site.rows();
std::vector<mmcif::Atom> atom_data;
for (auto &hem_atom: hem_atoms)
atom_data.emplace_back(hem_data, hem_atom);
structure.createNonpoly(entity_id, atom_data);
auto expected = R"(
data_TEST
#
_pdbx_nonpoly_scheme.asym_id A
_pdbx_nonpoly_scheme.ndb_seq_num 1
_pdbx_nonpoly_scheme.entity_id 1
_pdbx_nonpoly_scheme.mon_id HEM
_pdbx_nonpoly_scheme.pdb_seq_num 1
_pdbx_nonpoly_scheme.auth_seq_num 1
_pdbx_nonpoly_scheme.pdb_mon_id HEM
_pdbx_nonpoly_scheme.auth_mon_id HEM
_pdbx_nonpoly_scheme.pdb_strand_id A
_pdbx_nonpoly_scheme.pdb_ins_code .
#
loop_
_atom_site.id
_atom_site.auth_asym_id
_atom_site.label_alt_id
_atom_site.label_asym_id
_atom_site.label_atom_id
_atom_site.label_comp_id
_atom_site.label_entity_id
_atom_site.label_seq_id
_atom_site.type_symbol
_atom_site.group_PDB
_atom_site.pdbx_PDB_ins_code
_atom_site.Cartn_x
_atom_site.Cartn_y
_atom_site.Cartn_z
_atom_site.occupancy
_atom_site.B_iso_or_equiv
_atom_site.pdbx_formal_charge
_atom_site.auth_seq_id
_atom_site.auth_comp_id
_atom_site.auth_atom_id
_atom_site.pdbx_PDB_model_num
1 A ? A CHA HEM 1 . C HETATM ? -5.248 39.769 -0.250 1.00 7.67 ? 1 HEM CHA 1
2 A ? A CHB HEM 1 . C HETATM ? -3.774 36.790 3.280 1.00 7.05 ? 1 HEM CHB 1
3 A ? A CHC HEM 1 . C HETATM ? -2.879 33.328 0.013 1.00 7.69 ? 1 HEM CHC 1
4 A ? A CHD HEM 1 . C HETATM ? -4.342 36.262 -3.536 1.00 8.00 ? 1 HEM CHD 1
#
_chem_comp.id HEM
_chem_comp.type NON-POLYMER
_chem_comp.name 'PROTOPORPHYRIN IX CONTAINING FE'
_chem_comp.formula 'C34 H32 Fe N4 O4'
_chem_comp.formula_weight 616.487000
#
_pdbx_entity_nonpoly.entity_id 1
_pdbx_entity_nonpoly.name 'PROTOPORPHYRIN IX CONTAINING FE'
_pdbx_entity_nonpoly.comp_id HEM
#
_entity.id 1
_entity.type non-polymer
_entity.pdbx_description 'PROTOPORPHYRIN IX CONTAINING FE'
_entity.formula_weight 616.487000
#
_struct_asym.id A
_struct_asym.entity_id 1
_struct_asym.pdbx_blank_PDB_chainid_flag N
_struct_asym.pdbx_modified N
_struct_asym.details ?
#
)"_cf;
expected.loadDictionary("mmcif_pdbx.dic");
if (not (expected.firstDatablock() == structure.datablock()))
{
BOOST_TEST(false);
std::cout << expected.firstDatablock() << std::endl
<< std::endl
<< structure.datablock() << std::endl;
}
}
// // --------------------------------------------------------------------
// BOOST_AUTO_TEST_CASE(test_load_1)
// {
// mmcif::File cf(gTestDir / "5v3g.cif.gz");
// mmcif::Structure s(cf);
// for (auto &poly : s.polymers())
// {
// std::cout << std::string(80, '=') << std::endl;
// for (auto &res : poly)
// {
// std::cout << res << std::endl;
// for (auto &atom : res.atoms())
// std::cout << " " << atom << std::endl;
// }
// }
// }
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(test_atom_id)
{
auto data = R"(
data_TEST
#
_pdbx_nonpoly_scheme.asym_id A
_pdbx_nonpoly_scheme.ndb_seq_num 1
_pdbx_nonpoly_scheme.entity_id 1
_pdbx_nonpoly_scheme.mon_id HEM
_pdbx_nonpoly_scheme.pdb_seq_num 1
_pdbx_nonpoly_scheme.auth_seq_num 1
_pdbx_nonpoly_scheme.pdb_mon_id HEM
_pdbx_nonpoly_scheme.auth_mon_id HEM
_pdbx_nonpoly_scheme.pdb_strand_id A
_pdbx_nonpoly_scheme.pdb_ins_code .
#
loop_
_atom_site.id
_atom_site.auth_asym_id
_atom_site.label_alt_id
_atom_site.label_asym_id
_atom_site.label_atom_id
_atom_site.label_comp_id
_atom_site.label_entity_id
_atom_site.label_seq_id
_atom_site.type_symbol
_atom_site.group_PDB
_atom_site.pdbx_PDB_ins_code
_atom_site.Cartn_x
_atom_site.Cartn_y
_atom_site.Cartn_z
_atom_site.occupancy
_atom_site.B_iso_or_equiv
_atom_site.pdbx_formal_charge
_atom_site.auth_seq_id
_atom_site.auth_comp_id
_atom_site.auth_atom_id
_atom_site.pdbx_PDB_model_num
1 A ? A CHA HEM 1 . C HETATM ? -5.248 39.769 -0.250 1.00 7.67 ? 1 HEM CHA 1
3 A ? A CHB HEM 1 . C HETATM ? -3.774 36.790 3.280 1.00 7.05 ? 1 HEM CHB 1
2 A ? A CHC HEM 1 . C HETATM ? -2.879 33.328 0.013 1.00 7.69 ? 1 HEM CHC 1
4 A ? A CHD HEM 1 . C HETATM ? -4.342 36.262 -3.536 1.00 8.00 ? 1 HEM CHD 1
#
_chem_comp.id HEM
_chem_comp.type NON-POLYMER
_chem_comp.name 'PROTOPORPHYRIN IX CONTAINING FE'
_chem_comp.formula 'C34 H32 Fe N4 O4'
_chem_comp.formula_weight 616.487000
#
_pdbx_entity_nonpoly.entity_id 1
_pdbx_entity_nonpoly.name 'PROTOPORPHYRIN IX CONTAINING FE'
_pdbx_entity_nonpoly.comp_id HEM
#
_entity.id 1
_entity.type non-polymer
_entity.pdbx_description 'PROTOPORPHYRIN IX CONTAINING FE'
_entity.formula_weight 616.487000
#
_struct_asym.id A
_struct_asym.entity_id 1
_struct_asym.pdbx_blank_PDB_chainid_flag N
_struct_asym.pdbx_modified N
_struct_asym.details ?
#
)"_cf;
data.loadDictionary("mmcif_pdbx.dic");
mmcif::Structure s(data);
BOOST_CHECK_EQUAL(s.getAtomByID("1").authAtomID(), "CHA");
BOOST_CHECK_EQUAL(s.getAtomByID("2").authAtomID(), "CHC");
BOOST_CHECK_EQUAL(s.getAtomByID("3").authAtomID(), "CHB");
BOOST_CHECK_EQUAL(s.getAtomByID("4").authAtomID(), "CHD");
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(atom_numbers_1)
{
const std::filesystem::path test1(gTestDir / ".." / "examples" / "1cbs.cif.gz");
mmcif::File file(test1.string());
mmcif::Structure structure(file);
auto &db = file.data();
auto &atoms = structure.atoms();
auto ai = atoms.begin();
for (const auto &[id, label_asym_id, label_seq_id, label_atom_id, auth_seq_id, label_comp_id] :
db["atom_site"].rows<std::string,std::string,int,std::string,std::string,std::string>("id", "label_asym_id", "label_seq_id", "label_atom_id", "auth_seq_id", "label_comp_id"))
{
auto atom = structure.getAtomByID(id);
BOOST_CHECK_EQUAL(atom.labelAsymID(), label_asym_id);
BOOST_CHECK_EQUAL(atom.labelSeqID(), label_seq_id);
BOOST_CHECK_EQUAL(atom.labelAtomID(), label_atom_id);
BOOST_CHECK_EQUAL(atom.authSeqID(), auth_seq_id);
BOOST_CHECK_EQUAL(atom.labelCompID(), label_comp_id);
BOOST_ASSERT(ai != atoms.end());
BOOST_CHECK_EQUAL(ai->id(), id);
++ai;
}
BOOST_ASSERT(ai == atoms.end());
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(test_load_1)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / ".." / "examples" / "1cbs.cif.gz");
mmcif::File file(example.string());
auto &db = file.data();
mmcif::Structure s(file);
BOOST_CHECK(s.polymers().size() == 1);
auto &pdbx_poly_seq_scheme = db["pdbx_poly_seq_scheme"];
for (auto &poly : s.polymers())
{
BOOST_CHECK_EQUAL(poly.size(), pdbx_poly_seq_scheme.find("asym_id"_key == poly.asymID()).size());
}
}
BOOST_AUTO_TEST_CASE(remove_residue_1)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / ".." / "examples" / "1cbs.cif.gz");
mmcif::File file(example.string());
mmcif::Structure s(file);
s.removeResidue(s.getResidue("B"));
BOOST_CHECK_NO_THROW(s.validateAtoms());
}
/*-
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (c) 2021 NKI/AVL, Netherlands Cancer Institute
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#define BOOST_TEST_ALTERNATIVE_INIT_API
#include <boost/test/included/unit_test.hpp>
#include <stdexcept>
#include <cif++.hpp>
#include <cif++/structure/Structure.hpp>
// --------------------------------------------------------------------
cif::File operator""_cf(const char* text, size_t length)
{
struct membuf : public std::streambuf
{
membuf(char* text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char*>(text), length);
std::istream is(&buffer);
return cif::File(is);
}
// --------------------------------------------------------------------
std::filesystem::path gTestDir = std::filesystem::current_path();
bool init_unit_test()
{
cif::VERBOSE = 1;
// not a test, just initialize test dir
if (boost::unit_test::framework::master_test_suite().argc == 2)
gTestDir = boost::unit_test::framework::master_test_suite().argv[1];
// do this now, avoids the need for installing
cif::add_file_resource("mmcif_pdbx.dic", gTestDir / ".." / "rsrc" / "mmcif_pdbx.dic");
// initialize CCD location
cif::add_file_resource("components.cif", gTestDir / ".." / "data" / "ccd-subset.cif");
mmcif::CompoundFactory::instance().pushDictionary(gTestDir / "HEM.cif");
return true;
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(sugar_name_1)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / "1juh.cif.gz");
mmcif::File file(example.string());
mmcif::Structure s(file);
auto &db = s.datablock();
auto &entity = db["entity"];
auto &branches = s.branches();
BOOST_CHECK_EQUAL(branches.size(), 4);
for (auto &branch : branches)
{
auto entityID = branch.front().entityID();
auto name = entity.find1<std::string>("id"_key == entityID, "pdbx_description");
BOOST_CHECK_EQUAL(branch.name(), name);
}
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(create_sugar_1)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / "1juh.cif.gz");
mmcif::File file(example.string());
mmcif::Structure s(file);
// collect atoms from asym L first
auto &NAG = s.getResidue("L");
auto nagAtoms = NAG.atoms();
std::vector<std::vector<cif::Item>> ai;
auto &db = s.datablock();
auto &as = db["atom_site"];
for (auto r : as.find("label_asym_id"_key == "L"))
ai.emplace_back(r.begin(), r.end());
s.removeResidue(NAG);
auto &branch = s.createBranch(ai);
BOOST_CHECK_EQUAL(branch.name(), "2-acetamido-2-deoxy-beta-D-glucopyranose");
BOOST_CHECK_EQUAL(branch.size(), 1);
BOOST_CHECK_EQUAL(branch[0].atoms().size(), nagAtoms.size());
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(create_sugar_2)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / "1juh.cif.gz");
mmcif::File file(example.string());
mmcif::Structure s(file);
// Get branch for H
auto &bH = s.getBranchByAsymID("H");
BOOST_CHECK_EQUAL(bH.size(), 2);
std::vector<std::vector<cif::Item>> ai[2];
auto &db = s.datablock();
auto &as = db["atom_site"];
for (size_t i = 0; i < 2; ++i)
{
for (auto r : as.find("label_asym_id"_key == "H" and "auth_seq_id"_key == i + 1))
ai[i].emplace_back(r.begin(), r.end());
}
s.removeBranch(bH);
auto &bN = s.createBranch(ai[0]);
s.extendBranch(bN.asymID(), ai[1], 1, "O4");
BOOST_CHECK_EQUAL(bN.name(), "2-acetamido-2-deoxy-beta-D-glucopyranose-(1-4)-2-acetamido-2-deoxy-beta-D-glucopyranose");
BOOST_CHECK_EQUAL(bN.size(), 2);
file.save(gTestDir / "test-create_sugar_2.cif");
BOOST_CHECK_NO_THROW(mmcif::Structure s2(file));
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(delete_sugar_1)
{
using namespace cif::literals;
const std::filesystem::path example(gTestDir / "1juh.cif.gz");
mmcif::File file(example.string());
mmcif::Structure s(file);
// Get branch for H
auto &bG = s.getBranchByAsymID("G");
BOOST_CHECK_EQUAL(bG.size(), 4);
s.removeResidue(bG[1]);
BOOST_CHECK_EQUAL(bG.size(), 1);
auto &bN = s.getBranchByAsymID("G");
BOOST_CHECK_EQUAL(bN.name(), "2-acetamido-2-deoxy-beta-D-glucopyranose");
BOOST_CHECK_EQUAL(bN.size(), 1);
file.save(gTestDir / "test-create_sugar_3.cif");
BOOST_CHECK_NO_THROW(mmcif::Structure s2(file));
}
/*-
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (c) 2020 NKI/AVL, Netherlands Cancer Institute
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#define BOOST_TEST_ALTERNATIVE_INIT_API
// #define BOOST_TEST_MODULE LibCifPP_Test
#include <boost/test/included/unit_test.hpp>
#include <stdexcept>
// #include <cif++/DistanceMap.hpp>
#include <cif++/BondMap.hpp>
#include <cif++++.hpp>
#include <cif++Validator.hpp>
#include <cif++Parser.hpp>
namespace tt = boost::test_tools;
std::filesystem::path gTestDir = std::filesystem::current_path(); // filled in first test
// --------------------------------------------------------------------
cif::File operator""_cf(const char *text, size_t length)
{
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(text), length);
std::istream is(&buffer);
return cif::File(is);
}
// --------------------------------------------------------------------
bool init_unit_test()
{
cif::VERBOSE = 1;
// not a test, just initialize test dir
if (boost::unit_test::framework::master_test_suite().argc == 2)
gTestDir = boost::unit_test::framework::master_test_suite().argv[1];
// do this now, avoids the need for installing
cif::add_file_resource("mmcif_pdbx.dic", gTestDir / ".." / "rsrc" / "mmcif_pdbx.dic");
// initialize CCD location
cif::add_file_resource("components.cif", gTestDir / ".." / "data" / "ccd-subset.cif");
return true;
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(ut1)
{
// using namespace mmcif;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
1 aap
2 noot
3 mies
)"_cf;
auto &db = f.firstDatablock();
BOOST_CHECK(db.getName() == "TEST");
auto &test = db["test"];
BOOST_CHECK(test.size() == 3);
// wrong! the next lines will crash. And that's OK, don't do that
// for (auto r: test)
// test.erase(r);
// BOOST_CHECK(test.empty());
// test.purge();
auto n = test.erase(cif::Key("id") == 1, [](const cif::Row &r)
{
BOOST_CHECK_EQUAL(r["id"].as<int>(), 1);
BOOST_CHECK_EQUAL(r["name"].as<std::string>(), "aap"); });
BOOST_CHECK_EQUAL(n, 1);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(ut2)
{
// using namespace mmcif;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
_test.value
1 aap 1.0
2 noot 1.1
3 mies 1.2
)"_cf;
auto &db = f.firstDatablock();
BOOST_CHECK(db.getName() == "TEST");
auto &test = db["test"];
BOOST_CHECK(test.size() == 3);
int n = 0;
for (auto r : test.find(cif::Key("name") == "aap"))
{
BOOST_CHECK(++n == 1);
BOOST_CHECK(r["id"].as<int>() == 1);
BOOST_CHECK(r["name"].as<std::string>() == "aap");
BOOST_CHECK(r["value"].as<float>() == 1.0);
}
auto t = test.find(cif::Key("id") == 1);
BOOST_CHECK(not t.empty());
BOOST_CHECK(t.front()["name"].as<std::string>() == "aap");
auto t2 = test.find(cif::Key("value") == 1.2);
BOOST_CHECK(not t2.empty());
BOOST_CHECK(t2.front()["name"].as<std::string>() == "mies");
}
BOOST_AUTO_TEST_CASE(ut3)
{
using namespace cif::literals;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
_test.value
1 aap 1.0
2 noot 1.1
3 mies 1.2
4 boom .
5 roos ?
)"_cf;
auto &db = f.firstDatablock();
BOOST_CHECK(db.getName() == "TEST");
auto &test = db["test"];
BOOST_CHECK(test.size() == 5);
BOOST_CHECK(test.exists("value"_key == cif::null));
BOOST_CHECK(test.find("value"_key == cif::null).size() == 2);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(d1)
{
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
_item_type_list.detail
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
; code item types/single words ...
;
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
; text item types / multi-line text ...
;
int numb
'[+-]?[0-9]+'
; int item types are the subset of numbers that are the negative
or positive integers.
;
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_aliases.dictionary cif_core.dic
_item_aliases.version 2.0.1
_item_linked.child_name '_cat_2.parent_id'
_item_linked.parent_name '_cat_1.id'
_item_type.code code
save_
save__cat_1.name
_item.name '_cat_1.name'
_item.category_id cat_1
_item.mandatory_code yes
_item_aliases.dictionary cif_core.dic
_item_aliases.version 2.0.1
_item_type.code text
save_
save_cat_2
_category.description 'A second simple test category'
_category.id cat_2
_category.mandatory_code no
_category_key.name '_cat_2.id'
save_
save__cat_2.id
_item.name '_cat_2.id'
_item.category_id cat_2
_item.mandatory_code yes
_item_aliases.dictionary cif_core.dic
_item_aliases.version 2.0.1
_item_type.code int
save_
save__cat_2.parent_id
_item.name '_cat_2.parent_id'
_item.category_id cat_2
_item.mandatory_code yes
_item_aliases.dictionary cif_core.dic
_item_aliases.version 2.0.1
_item_type.code code
save_
save__cat_2.desc
_item.name '_cat_2.desc'
_item.category_id cat_2
_item.mandatory_code yes
_item_aliases.dictionary cif_core.dic
_item_aliases.version 2.0.1
_item_type.code text
save_
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
_cat_1.name
1 Aap
2 Noot
3 Mies
loop_
_cat_2.id
_cat_2.parent_id
_cat_2.desc
1 1 'Een dier'
2 1 'Een andere aap'
3 2 'walnoot bijvoorbeeld'
)";
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
f.setValidator(&validator);
auto &cat1 = f.firstDatablock()["cat_1"];
auto &cat2 = f.firstDatablock()["cat_2"];
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 3);
cat1.erase(cif::Key("id") == 1);
BOOST_CHECK(cat1.size() == 2);
BOOST_CHECK(cat2.size() == 1);
// BOOST_CHECK_THROW(cat2.emplace({
// { "id", 4 },
// { "parent_id", 4 },
// { "desc", "moet fout gaan" }
// }), std::exception);
BOOST_CHECK_THROW(cat2.emplace({{"id", "vijf"}, // <- invalid value
{"parent_id", 2},
{"desc", "moet fout gaan"}}),
std::exception);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(d2)
{
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
_item_type_list.detail
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
; code item types/single words ...
;
ucode uchar
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
; code item types/single words, case insensitive
;
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
; text item types / multi-line text ...
;
int numb
'[+-]?[0-9]+'
; int item types are the subset of numbers that are the negative
or positive integers.
;
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code code
save_
save__cat_1.c
_item.name '_cat_1.c'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code ucode
save_
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
f.setValidator(&validator);
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
_cat_1.c
aap Aap
noot Noot
mies Mies
)";
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
auto &cat1 = f.firstDatablock()["cat_1"];
BOOST_CHECK(cat1.size() == 3);
cat1.erase(cif::Key("id") == "AAP");
BOOST_CHECK(cat1.size() == 3);
cat1.erase(cif::Key("id") == "noot");
BOOST_CHECK(cat1.size() == 2);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(d3)
{
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
int numb
'[+-]?[0-9]+'
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_linked.child_name '_cat_2.parent_id'
_item_linked.parent_name '_cat_1.id'
_item_type.code code
save_
save__cat_1.name1
_item.name '_cat_1.name1'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code text
save_
save__cat_1.name2
_item.name '_cat_1.name2'
_item.category_id cat_1
_item.mandatory_code no
_item_linked.child_name '_cat_2.name2'
_item_linked.parent_name '_cat_1.name2'
_item_type.code text
save_
save_cat_2
_category.description 'A second simple test category'
_category.id cat_2
_category.mandatory_code no
_category_key.name '_cat_2.id'
save_
save__cat_2.id
_item.name '_cat_2.id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.parent_id
_item.name '_cat_2.parent_id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code code
save_
save__cat_2.name2
_item.name '_cat_2.name2'
_item.category_id cat_2
_item.mandatory_code no
_item_type.code text
save_
save__cat_2.desc
_item.name '_cat_2.desc'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code text
save_
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
f.setValidator(&validator);
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
_cat_1.name1
_cat_1.name2
1 Aap aap
2 Noot noot
3 Mies mies
loop_
_cat_2.id
_cat_2.parent_id
_cat_2.name2
_cat_2.desc
1 1 aap 'Een dier'
2 1 . 'Een andere aap'
3 2 noot 'walnoot bijvoorbeeld'
4 2 n2 hazelnoot
)";
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
auto &cat1 = f.firstDatablock()["cat_1"];
auto &cat2 = f.firstDatablock()["cat_2"];
// check a rename in parent and child
for (auto r : cat1.find(cif::Key("id") == 1))
{
r["id"] = 10;
break;
}
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 4);
BOOST_CHECK(cat1.find(cif::Key("id") == 1).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 1).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 10).size() == 2);
// check a rename in parent and child, this time only one child should be renamed
for (auto r : cat1.find(cif::Key("id") == 2))
{
r["id"] = 20;
break;
}
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 4);
BOOST_CHECK(cat1.find(cif::Key("id") == 2).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 20).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 2).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 20).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 2 and cif::Key("name2") == "noot").size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 2 and cif::Key("name2") == "n2").size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 20 and cif::Key("name2") == "noot").size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 20 and cif::Key("name2") == "n2").size() == 0);
// // --------------------------------------------------------------------
// cat1.erase(cif::Key("id") == 10);
// BOOST_CHECK(cat1.size() == 2);
// BOOST_CHECK(cat2.size() == 2);
// cat1.erase(cif::Key("id") == 20);
// BOOST_CHECK(cat1.size() == 1);
// BOOST_CHECK(cat2.size() == 1);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(d4)
{
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
int numb
'[+-]?[0-9]+'
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_linked.child_name '_cat_2.parent_id'
_item_linked.parent_name '_cat_1.id'
_item_type.code int
save_
save__cat_1.id2
_item.name '_cat_1.id2'
_item.category_id cat_1
_item.mandatory_code no
_item_linked.child_name '_cat_2.parent_id2'
_item_linked.parent_name '_cat_1.id2'
_item_type.code code
save_
save__cat_1.id3
_item.name '_cat_1.id3'
_item.category_id cat_1
_item.mandatory_code no
_item_linked.child_name '_cat_2.parent_id3'
_item_linked.parent_name '_cat_1.id3'
_item_type.code text
save_
save_cat_2
_category.description 'A second simple test category'
_category.id cat_2
_category.mandatory_code no
_category_key.name '_cat_2.id'
save_
save__cat_2.id
_item.name '_cat_2.id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.parent_id
_item.name '_cat_2.parent_id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.parent_id2
_item.name '_cat_2.parent_id2'
_item.category_id cat_2
_item.mandatory_code no
_item_type.code code
save_
save__cat_2.parent_id3
_item.name '_cat_2.parent_id3'
_item.category_id cat_2
_item.mandatory_code no
_item_type.code code
save_
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
f.setValidator(&validator);
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
_cat_1.id2
_cat_1.id3
1 aap aap
2 . noot
3 mies .
4 . .
loop_
_cat_2.id
_cat_2.parent_id
_cat_2.parent_id2
_cat_2.parent_id3
1 1 aap aap
2 1 . x
3 1 aap .
4 2 noot noot
5 2 . noot
6 2 noot .
7 2 . .
8 3 mies mies
9 3 . mies
10 3 mies .
11 4 roos roos
12 4 . roos
13 4 roos .
)";
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
auto &cat1 = f.firstDatablock()["cat_1"];
auto &cat2 = f.firstDatablock()["cat_2"];
// check a rename in parent and child
for (auto r : cat1.find(cif::Key("id") == 1))
{
r["id"] = 10;
break;
}
BOOST_CHECK(cat1.size() == 4);
BOOST_CHECK(cat2.size() == 13);
BOOST_CHECK(cat1.find(cif::Key("id") == 1).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 1).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 10).size() == 2);
for (auto r : cat1.find(cif::Key("id") == 2))
{
r["id"] = 20;
break;
}
BOOST_CHECK(cat1.size() == 4);
BOOST_CHECK(cat2.size() == 13);
BOOST_CHECK(cat1.find(cif::Key("id") == 2).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 20).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 2).size() == 2);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 20).size() == 2);
for (auto r : cat1.find(cif::Key("id") == 3))
{
r["id"] = 30;
break;
}
BOOST_CHECK(cat1.size() == 4);
BOOST_CHECK(cat2.size() == 13);
BOOST_CHECK(cat1.find(cif::Key("id") == 3).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 30).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 3).size() == 2);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 30).size() == 1);
for (auto r : cat1.find(cif::Key("id") == 4))
{
r["id"] = 40;
break;
}
BOOST_CHECK(cat1.size() == 4);
BOOST_CHECK(cat2.size() == 13);
BOOST_CHECK(cat1.find(cif::Key("id") == 4).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 4).size() == 3);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 40).size() == 0);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(d5)
{
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
int numb
'[+-]?[0-9]+'
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code int
save_
save_cat_2
_category.description 'A second simple test category'
_category.id cat_2
_category.mandatory_code no
_category_key.name '_cat_2.id'
save_
save__cat_2.id
_item.name '_cat_2.id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.parent_id
_item.name '_cat_2.parent_id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.parent_id2
_item.name '_cat_2.parent_id2'
_item.category_id cat_2
_item.mandatory_code no
_item_type.code code
save_
save__cat_2.parent_id3
_item.name '_cat_2.parent_id3'
_item.category_id cat_2
_item.mandatory_code no
_item_type.code code
save_
loop_
_pdbx_item_linked_group_list.child_category_id
_pdbx_item_linked_group_list.link_group_id
_pdbx_item_linked_group_list.child_name
_pdbx_item_linked_group_list.parent_name
_pdbx_item_linked_group_list.parent_category_id
cat_2 1 '_cat_2.parent_id' '_cat_1.id' cat_1
cat_2 2 '_cat_2.parent_id2' '_cat_1.id' cat_1
cat_2 3 '_cat_2.parent_id3' '_cat_1.id' cat_1
loop_
_pdbx_item_linked_group.category_id
_pdbx_item_linked_group.link_group_id
_pdbx_item_linked_group.label
cat_2 1 cat_2:cat_1:1
cat_2 2 cat_2:cat_1:2
cat_2 3 cat_2:cat_1:3
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
f.setValidator(&validator);
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
1
2
3
loop_
_cat_2.id
_cat_2.parent_id
_cat_2.parent_id2
_cat_2.parent_id3
1 1 ? ?
2 ? 1 ?
3 ? ? 1
4 2 2 ?
5 2 ? 2
6 ? 2 2
7 3 3 3
)";
// --------------------------------------------------------------------
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
auto &cat1 = f.firstDatablock()["cat_1"];
auto &cat2 = f.firstDatablock()["cat_2"];
// --------------------------------------------------------------------
// check iterate children
auto PR2set = cat1.find(cif::Key("id") == 2);
BOOST_ASSERT(PR2set.size() == 1);
auto PR2 = PR2set.front();
BOOST_CHECK(PR2["id"].as<int>() == 2);
auto CR2set = cat1.getChildren(PR2, "cat_2");
BOOST_ASSERT(CR2set.size() == 3);
std::vector<int> CRids;
std::transform(CR2set.begin(), CR2set.end(), std::back_inserter(CRids), [](cif::Row r)
{ return r["id"].as<int>(); });
std::sort(CRids.begin(), CRids.end());
BOOST_CHECK(CRids == std::vector<int>({4, 5, 6}));
// check a rename in parent and child
for (auto r : cat1.find(cif::Key("id") == 1))
{
r["id"] = 10;
break;
}
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 7);
BOOST_CHECK(cat1.find(cif::Key("id") == 1).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 1).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 1).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 1).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 10).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 10).size() == 1);
for (auto r : cat1.find(cif::Key("id") == 2))
{
r["id"] = 20;
break;
}
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 7);
BOOST_CHECK(cat1.find(cif::Key("id") == 2).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 20).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 2).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 2).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 2).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 20).size() == 2);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 20).size() == 2);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 20).size() == 2);
for (auto r : cat1.find(cif::Key("id") == 3))
{
r["id"] = 30;
break;
}
BOOST_CHECK(cat1.size() == 3);
BOOST_CHECK(cat2.size() == 7);
BOOST_CHECK(cat1.find(cif::Key("id") == 3).size() == 0);
BOOST_CHECK(cat1.find(cif::Key("id") == 30).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 3).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 3).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 3).size() == 0);
BOOST_CHECK(cat2.find(cif::Key("parent_id") == 30).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id2") == 30).size() == 1);
BOOST_CHECK(cat2.find(cif::Key("parent_id3") == 30).size() == 1);
// test delete
cat1.erase(cif::Key("id") == 10);
BOOST_CHECK(cat1.size() == 2);
BOOST_CHECK(cat2.size() == 4);
cat1.erase(cif::Key("id") == 20);
BOOST_CHECK(cat1.size() == 1);
BOOST_CHECK(cat2.size() == 1);
cat1.erase(cif::Key("id") == 30);
BOOST_CHECK(cat1.size() == 0);
BOOST_CHECK(cat2.size() == 0);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(c1)
{
cif::VERBOSE = 1;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
1 aap
2 noot
3 mies
4 .
5 ?
)"_cf;
auto &db = f.firstDatablock();
for (auto r : db["test"].find(cif::Key("id") == 1))
{
const auto &[id, name] = r.get<int, std::string>({"id", "name"});
BOOST_CHECK(id == 1);
BOOST_CHECK(name == "aap");
}
for (auto r : db["test"].find(cif::Key("id") == 4))
{
const auto &[id, name] = r.get<int, std::string>({"id", "name"});
BOOST_CHECK(id == 4);
BOOST_CHECK(name.empty());
}
for (auto r : db["test"].find(cif::Key("id") == 5))
{
const auto &[id, name] = r.get<int, std::string>({"id", "name"});
BOOST_CHECK(id == 5);
BOOST_CHECK(name.empty());
}
// optional
for (auto r : db["test"])
{
const auto &[id, name] = r.get<int, std::optional<std::string>>({"id", "name"});
switch (id)
{
case 1: BOOST_CHECK(name == "aap"); break;
case 2: BOOST_CHECK(name == "noot"); break;
case 3: BOOST_CHECK(name == "mies"); break;
case 4:
case 5: BOOST_CHECK(not name); break;
default:
BOOST_CHECK(false);
}
}
}
BOOST_AUTO_TEST_CASE(c2)
{
cif::VERBOSE = 1;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
1 aap
2 noot
3 mies
4 .
5 ?
)"_cf;
auto &db = f.firstDatablock();
// query tests
for (const auto &[id, name] : db["test"].rows<int, std::optional<std::string>>("id", "name"))
{
switch (id)
{
case 1: BOOST_CHECK(name == "aap"); break;
case 2: BOOST_CHECK(name == "noot"); break;
case 3: BOOST_CHECK(name == "mies"); break;
case 4:
case 5: BOOST_CHECK(not name); break;
default:
BOOST_CHECK(false);
}
}
}
BOOST_AUTO_TEST_CASE(c3)
{
cif::VERBOSE = 1;
auto f = R"(data_TEST
#
loop_
_test.id
_test.name
1 aap
2 noot
3 mies
4 .
5 ?
)"_cf;
auto &db = f.firstDatablock();
// query tests
for (const auto &[id, name] : db["test"].find<int, std::optional<std::string>>(cif::All(), "id", "name"))
{
switch (id)
{
case 1: BOOST_CHECK(name == "aap"); break;
case 2: BOOST_CHECK(name == "noot"); break;
case 3: BOOST_CHECK(name == "mies"); break;
case 4:
case 5: BOOST_CHECK(not name); break;
default:
BOOST_CHECK(false);
}
}
const auto &[id, name] = db["test"].find1<int, std::string>(cif::Key("id") == 1, "id", "name");
BOOST_CHECK(id == 1);
BOOST_CHECK(name == "aap");
}
// --------------------------------------------------------------------
// rename test
BOOST_AUTO_TEST_CASE(r1)
{
/*
Rationale:
The pdbx_mmcif dictionary contains inconsistent child-parent relations. E.g. atom_site is parent
of pdbx_nonpoly_scheme which itself is a parent of pdbx_entity_nonpoly. If I want to rename a residue
I cannot update pdbx_nonpoly_scheme since changing a parent changes children, but not vice versa.
But if I change the comp_id in atom_site, the pdbx_nonpoly_scheme is update, that's good, and then
pdbx_entity_nonpoly is updated and that's bad.
The idea is now that if we update a parent and a child that must change as well, we first check
if there are more parents of this child that will not change. In that case we have to split the
child into two, one with the new value and one with the old. We then of course have to split all
children of this split row that are direct children.
*/
const char dict[] = R"(
data_test_dict.dic
_datablock.id test_dict.dic
_datablock.description
;
A test dictionary
;
_dictionary.title test_dict.dic
_dictionary.datablock_id test_dict.dic
_dictionary.version 1.0
loop_
_item_type_list.code
_item_type_list.primitive_code
_item_type_list.construct
code char
'[][_,.;:"&<>()/\{}'`~!@#$%A-Za-z0-9*|+-]*'
text char
'[][ \n\t()_,.;:"&<>/\{}'`~!@#$%?+=*A-Za-z0-9|^-]*'
int numb
'[+-]?[0-9]+'
save_cat_1
_category.description 'A simple test category'
_category.id cat_1
_category.mandatory_code no
_category_key.name '_cat_1.id'
save_
save__cat_1.id
_item.name '_cat_1.id'
_item.category_id cat_1
_item.mandatory_code yes
_item_linked.child_name '_cat_2.parent_id'
_item_linked.parent_name '_cat_1.id'
_item_type.code int
save_
save__cat_1.name
_item.name '_cat_1.name'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code code
save_
save__cat_1.desc
_item.name '_cat_1.desc'
_item.category_id cat_1
_item.mandatory_code yes
_item_type.code text
save_
save_cat_2
_category.description 'A second simple test category'
_category.id cat_2
_category.mandatory_code no
_category_key.name '_cat_2.id'
save_
save__cat_2.id
_item.name '_cat_2.id'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.name
_item.name '_cat_2.name'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code code
save_
save__cat_2.num
_item.name '_cat_2.num'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code int
save_
save__cat_2.desc
_item.name '_cat_2.desc'
_item.category_id cat_2
_item.mandatory_code yes
_item_type.code text
save_
save_cat_3
_category.description 'A third simple test category'
_category.id cat_3
_category.mandatory_code no
_category_key.name '_cat_3.id'
save_
save__cat_3.id
_item.name '_cat_3.id'
_item.category_id cat_3
_item.mandatory_code yes
_item_type.code int
save_
save__cat_3.name
_item.name '_cat_3.name'
_item.category_id cat_3
_item.mandatory_code yes
_item_type.code code
save_
save__cat_3.num
_item.name '_cat_3.num'
_item.category_id cat_3
_item.mandatory_code yes
_item_type.code int
save_
loop_
_pdbx_item_linked_group_list.child_category_id
_pdbx_item_linked_group_list.link_group_id
_pdbx_item_linked_group_list.child_name
_pdbx_item_linked_group_list.parent_name
_pdbx_item_linked_group_list.parent_category_id
cat_1 1 '_cat_1.name' '_cat_2.name' cat_2
cat_2 1 '_cat_2.name' '_cat_3.name' cat_3
cat_2 1 '_cat_2.num' '_cat_3.num' cat_3
)";
struct membuf : public std::streambuf
{
membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} buffer(const_cast<char *>(dict), sizeof(dict) - 1);
std::istream is_dict(&buffer);
cif::Validator validator("test", is_dict);
cif::File f;
f.setValidator(&validator);
// --------------------------------------------------------------------
const char data[] = R"(
data_test
loop_
_cat_1.id
_cat_1.name
_cat_1.desc
1 aap Aap
2 noot Noot
3 mies Mies
loop_
_cat_2.id
_cat_2.name
_cat_2.num
_cat_2.desc
1 aap 1 'Een dier'
2 aap 2 'Een andere aap'
3 noot 1 'walnoot bijvoorbeeld'
loop_
_cat_3.id
_cat_3.name
_cat_3.num
1 aap 1
2 aap 2
)";
using namespace cif::literals;
struct data_membuf : public std::streambuf
{
data_membuf(char *text, size_t length)
{
this->setg(text, text, text + length);
}
} data_buffer(const_cast<char *>(data), sizeof(data) - 1);
std::istream is_data(&data_buffer);
f.load(is_data);
auto &cat1 = f.firstDatablock()["cat_1"];
auto &cat2 = f.firstDatablock()["cat_2"];
auto &cat3 = f.firstDatablock()["cat_3"];
cat3.update_value("name"_key == "aap" and "num"_key == 1, "name", "aapje");
BOOST_CHECK(cat3.size() == 2);
{
int id, num;
std::string name;
cif::tie(id, name, num) = cat3.front().get("id", "name", "num");
BOOST_CHECK(id == 1);
BOOST_CHECK(num == 1);
BOOST_CHECK(name == "aapje");
cif::tie(id, name, num) = cat3.back().get("id", "name", "num");
BOOST_CHECK(id == 2);
BOOST_CHECK(num == 2);
BOOST_CHECK(name == "aap");
}
int i = 0;
for (const auto &[id, name, num, desc] : cat2.rows<int, std::string, int, std::string>("id", "name", "num", "desc"))
{
switch (++i)
{
case 1:
BOOST_CHECK(id == 1);
BOOST_CHECK(num == 1);
BOOST_CHECK(name == "aapje");
BOOST_CHECK(desc == "Een dier");
break;
case 2:
BOOST_CHECK(id == 2);
BOOST_CHECK(num == 2);
BOOST_CHECK(name == "aap");
BOOST_CHECK(desc == "Een andere aap");
break;
case 3:
BOOST_CHECK(id == 3);
BOOST_CHECK(num == 1);
BOOST_CHECK(name == "noot");
BOOST_CHECK(desc == "walnoot bijvoorbeeld");
break;
default:
BOOST_FAIL("Unexpected record");
}
}
BOOST_CHECK(cat1.size() == 4);
i = 0;
for (const auto &[id, name, desc] : cat1.rows<int, std::string, std::string>("id", "name", "desc"))
{
switch (++i)
{
case 1:
BOOST_CHECK(id == 1);
BOOST_CHECK(name == "aapje");
BOOST_CHECK(desc == "Aap");
break;
case 2:
BOOST_CHECK(id == 2);
BOOST_CHECK(name == "noot");
BOOST_CHECK(desc == "Noot");
break;
case 3:
BOOST_CHECK(id == 3);
BOOST_CHECK(name == "mies");
BOOST_CHECK(desc == "Mies");
break;
case 4:
BOOST_CHECK(id == 4);
BOOST_CHECK(name == "aap");
BOOST_CHECK(desc == "Aap");
break;
default:
BOOST_FAIL("Unexpected record");
}
}
f.save(std::cout);
}
// --------------------------------------------------------------------
BOOST_AUTO_TEST_CASE(bondmap_1)
{
cif::VERBOSE = 2;
// sections taken from CCD compounds.cif
auto components = R"(
data_ASN
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
ASN N CA SING N N 1
ASN N H SING N N 2
ASN N H2 SING N N 3
ASN CA C SING N N 4
ASN CA CB SING N N 5
ASN CA HA SING N N 6
ASN C O DOUB N N 7
ASN C OXT SING N N 8
ASN CB CG SING N N 9
ASN CB HB2 SING N N 10
ASN CB HB3 SING N N 11
ASN CG OD1 DOUB N N 12
ASN CG ND2 SING N N 13
ASN ND2 HD21 SING N N 14
ASN ND2 HD22 SING N N 15
ASN OXT HXT SING N N 16
data_PHE
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
PHE N CA SING N N 1
PHE N H SING N N 2
PHE N H2 SING N N 3
PHE CA C SING N N 4
PHE CA CB SING N N 5
PHE CA HA SING N N 6
PHE C O DOUB N N 7
PHE C OXT SING N N 8
PHE CB CG SING N N 9
PHE CB HB2 SING N N 10
PHE CB HB3 SING N N 11
PHE CG CD1 DOUB Y N 12
PHE CG CD2 SING Y N 13
PHE CD1 CE1 SING Y N 14
PHE CD1 HD1 SING N N 15
PHE CD2 CE2 DOUB Y N 16
PHE CD2 HD2 SING N N 17
PHE CE1 CZ DOUB Y N 18
PHE CE1 HE1 SING N N 19
PHE CE2 CZ SING Y N 20
PHE CE2 HE2 SING N N 21
PHE CZ HZ SING N N 22
PHE OXT HXT SING N N 23
data_PRO
loop_
_chem_comp_bond.comp_id
_chem_comp_bond.atom_id_1
_chem_comp_bond.atom_id_2
_chem_comp_bond.value_order
_chem_comp_bond.pdbx_aromatic_flag
_chem_comp_bond.pdbx_stereo_config
_chem_comp_bond.pdbx_ordinal
PRO N CA SING N N 1
PRO N CD SING N N 2
PRO N H SING N N 3
PRO CA C SING N N 4
PRO CA CB SING N N 5
PRO CA HA SING N N 6
PRO C O DOUB N N 7
PRO C OXT SING N N 8
PRO CB CG SING N N 9
PRO CB HB2 SING N N 10
PRO CB HB3 SING N N 11
PRO CG CD SING N N 12
PRO CG HG2 SING N N 13
PRO CG HG3 SING N N 14
PRO CD HD2 SING N N 15
PRO CD HD3 SING N N 16
PRO OXT HXT SING N N 17
)"_cf;
const std::filesystem::path example(gTestDir / ".." / "examples" / "1cbs.cif.gz");
mmcif::File file(example.string());
mmcif::Structure structure(file);
(void)file.isValid();
mmcif::BondMap bm(structure);
// Test the bonds of the first three residues, that's PRO A 1, ASN A 2, PHE A 3
for (const auto &[compound, seqnr] : std::initializer_list<std::tuple<std::string, int>>{{"PRO", 1}, {"ASN", 2}, {"PHE", 3}})
{
auto &res = structure.getResidue("A", compound, seqnr, "");
auto atoms = res.atoms();
auto dc = components.get(compound);
BOOST_ASSERT(dc != nullptr);
auto cc = dc->get("chem_comp_bond");
BOOST_ASSERT(cc != nullptr);
std::set<std::tuple<std::string, std::string>> bonded;
for (const auto &[atom_id_1, atom_id_2] : cc->rows<std::string, std::string>("atom_id_1", "atom_id_2"))
{
if (atom_id_1 > atom_id_2)
bonded.insert({atom_id_2, atom_id_1});
else
bonded.insert({atom_id_1, atom_id_2});
}
for (size_t i = 0; i + 1 < atoms.size(); ++i)
{
auto label_i = atoms[i].labelAtomID();
for (size_t j = i + 1; j < atoms.size(); ++j)
{
auto label_j = atoms[j].labelAtomID();
bool bonded_1 = bm(atoms[i], atoms[j]);
bool bonded_1_i = bm(atoms[j], atoms[i]);
bool bonded_t = label_i > label_j
? bonded.count({label_j, label_i})
: bonded.count({label_i, label_j});
BOOST_CHECK(bonded_1 == bonded_t);
BOOST_CHECK(bonded_1_i == bonded_t);
}
}
}
// And check the inter-aminoacid links
auto &poly = structure.polymers().front();
for (size_t i = 0; i + 1 < poly.size(); ++i)
{
auto C = poly[i].atomByID("C");
auto N = poly[i + 1].atomByID("N");
BOOST_CHECK(bm(C, N));
BOOST_CHECK(bm(N, C));
}
}
BOOST_AUTO_TEST_CASE(bondmap_2)
{
BOOST_CHECK_THROW(mmcif::BondMap::atomIDsForCompound("UN_"), mmcif::BondMapException);
mmcif::CompoundFactory::instance().pushDictionary(gTestDir / "UN_.cif");
BOOST_CHECK(mmcif::BondMap::atomIDsForCompound("UN_").empty() == false);
}
BOOST_AUTO_TEST_CASE(reading_file_1)
{
std::istringstream is("Hello, world!");
cif::File file;
BOOST_CHECK_THROW(file.load(is), std::runtime_error);
}
// 3d tests
using namespace mmcif;
BOOST_AUTO_TEST_CASE(t1)
{
// std::random_device rnd;
// std::mt19937 gen(rnd());
// std::uniform_real_distribution<float> dis(0, 1);
// Quaternion q{ dis(gen), dis(gen), dis(gen), dis(gen) };
// q = Normalize(q);
// Quaternion q{ 0.1, 0.2, 0.3, 0.4 };
Quaternion q{0.5, 0.5, 0.5, 0.5};
q = Normalize(q);
const auto &&[angle0, axis0] = QuaternionToAngleAxis(q);
std::vector<Point> p1{
{16.979, 13.301, 44.555},
{18.150, 13.525, 43.680},
{18.656, 14.966, 43.784},
{17.890, 15.889, 44.078},
{17.678, 13.270, 42.255},
{16.248, 13.734, 42.347},
{15.762, 13.216, 43.724}};
auto p2 = p1;
CenterPoints(p1);
for (auto &p : p2)
p.rotate(q);
CenterPoints(p2);
auto q2 = AlignPoints(p1, p2);
const auto &&[angle, axis] = QuaternionToAngleAxis(q2);
BOOST_TEST(std::fmod(360 + angle, 360) == std::fmod(360 - angle0, 360), tt::tolerance(0.01));
for (auto &p : p1)
p.rotate(q2);
float rmsd = RMSd(p1, p2);
BOOST_TEST(rmsd < 1e-5);
// std::cout << "rmsd: " << RMSd(p1, p2) << std::endl;
}
BOOST_AUTO_TEST_CASE(t2)
{
Point p[] = {
{ 1, 1, 0 },
{ 2, 1, 0 },
{ 1, 2, 0 }
};
Point xp = mmcif::CrossProduct(p[1] - p[0], p[2] - p[0]);
Quaternion q = ConstructFromAngleAxis(45, xp); //mmcif::Normalize(Quaternion{45 * mmcif::kPI / 180, xp.mX, xp.mY, xp.mZ});
auto &&[angle, axis] = mmcif::QuaternionToAngleAxis(q);
BOOST_TEST(angle == 45, tt::tolerance(0.01));
}
BOOST_AUTO_TEST_CASE(t3)
{
Point p[] = {
{ 1, 1, 0 },
{ 2, 1, 0 },
{ 1, 2, 0 }
};
Point xp = mmcif::CrossProduct(p[1] - p[0], p[2] - p[0]);
Quaternion q = ConstructFromAngleAxis(45, xp); //mmcif::Normalize(Quaternion{45 * mmcif::kPI / 180, xp.mX, xp.mY, xp.mZ});
Point v = p[1];
v -= p[0];
v.rotate(q);
v += p[0];
std::cout << v << std::endl;
double a = mmcif::Angle(v, p[0], p[1]);
BOOST_TEST(a == 45, tt::tolerance(0.01));
}
BOOST_AUTO_TEST_CASE(parser_test_1)
{
auto data1 = R"(
data_QM
_test.text ??
)"_cf;
auto &db1 = data1.firstDatablock();
auto &test1 = db1["test"];
BOOST_CHECK_EQUAL(test1.size(), 1);
for (auto r : test1)
{
const auto &[text] = r.get<std::string>({"text"});
BOOST_CHECK_EQUAL(text, "??");
}
std::stringstream ss;
data1.save(ss);
auto data2 = cif::File(ss);
auto &db2 = data2.firstDatablock();
auto &test2 = db2["test"];
BOOST_CHECK_EQUAL(test2.size(), 1);
for (auto r : test2)
{
const auto &[text] = r.get<std::string>({"text"});
BOOST_CHECK_EQUAL(text, "??");
}
}
BOOST_AUTO_TEST_CASE(output_test_1)
{
auto data1 = R"(
data_Q
loop_
_test.text
"stop_the_crap"
'and stop_ this too'
'data_dinges'
'blablaglobal_bla'
boo.data_.whatever
)"_cf;
auto &db1 = data1.firstDatablock();
auto &test1 = db1["test"];
struct T {
const char *s;
bool q;
} kS[] = {
{ "stop_the_crap", false },
{ "and stop_ this too", false },
{ "data_dinges", false },
{ "blablaglobal_bla", false },
{ "boo.data_.whatever", true }
};
BOOST_CHECK_EQUAL(test1.size(), sizeof(kS) / sizeof(T));
size_t i = 0;
for (auto r : test1)
{
const auto &[text] = r.get<std::string>({"text"});
BOOST_CHECK_EQUAL(text, kS[i].s);
BOOST_CHECK_EQUAL(cif::isUnquotedString(kS[i].s), kS[i].q);
++i;
}
std::stringstream ss;
data1.save(ss);
auto data2 = cif::File(ss);
auto &db2 = data2.firstDatablock();
auto &test2 = db2["test"];
BOOST_CHECK_EQUAL(test2.size(), sizeof(kS) / sizeof(T));
i = 0;
for (auto r : test2)
{
const auto &[text] = r.get<std::string>({"text"});
BOOST_CHECK_EQUAL(text, kS[i++].s);
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment