mirror of
https://gitlab.com/scemama/QCaml.git
synced 2024-12-22 04:13:33 +01:00
Reading both XYZ and Zmatrix
This commit is contained in:
parent
e909bb9abb
commit
dad44067f7
@ -1,11 +1,15 @@
|
||||
(** General basis set read from a file *)
|
||||
|
||||
type primitive = {
|
||||
exponent: float ;
|
||||
coefficient: float
|
||||
}
|
||||
|
||||
type contracted_shell = Angular_momentum.t * (primitive array)
|
||||
type element_name = string
|
||||
|
||||
type gaussian_basis_set = string * (contracted_shell array)
|
||||
type general_contracted_shell = Angular_momentum.t * (primitive array)
|
||||
|
||||
type basis_set = element_name * (general_contracted_shell array)
|
||||
|
||||
|
||||
let string_of_primitive ?id prim =
|
||||
@ -30,6 +34,9 @@ let string_of_contracted_shell_array a =
|
||||
|> Array.to_list
|
||||
|> String.concat "\n"
|
||||
|
||||
|
||||
let to_string (name, contracted_shell_array) =
|
||||
Printf.sprintf "%s\n%s" name (string_of_contracted_shell_array contracted_shell_array)
|
||||
|
||||
|
||||
|
||||
|
@ -1,7 +1,7 @@
|
||||
{
|
||||
exception SyntaxError of string
|
||||
|
||||
open Basis_parser
|
||||
open Gamess_parser
|
||||
|
||||
}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* Parses basis sets in GAMESS format */
|
||||
/* Parses basis sets GAMESS format */
|
||||
|
||||
%{
|
||||
|
||||
@ -13,7 +13,7 @@
|
||||
%token EOF
|
||||
|
||||
%start input
|
||||
%type <Basis.gaussian_basis_set> input
|
||||
%type <Basis.basis_set> input
|
||||
|
||||
%% /* Grammar rules and actions follow */
|
||||
|
||||
@ -46,3 +46,4 @@ primitive:
|
||||
| INTEGER FLOAT FLOAT EOL { Basis.{exponent=$2 ; coefficient=$3 } }
|
||||
|
||||
|
||||
|
21
Basis/Gamess_reader.ml
Normal file
21
Basis/Gamess_reader.ml
Normal file
@ -0,0 +1,21 @@
|
||||
(** Read a basis set file in GAMESS format and return an association list where the key is an
|
||||
Element.t and the value is the parsed basis set. *)
|
||||
let read ~filename =
|
||||
let lexbuf =
|
||||
let ic = open_in filename in
|
||||
Lexing.from_channel ic
|
||||
in
|
||||
let rec aux accu =
|
||||
try
|
||||
let element, basis =
|
||||
Gamess_parser.input Basis_lexer.read_all lexbuf
|
||||
in
|
||||
let key =
|
||||
Element.of_string element
|
||||
in
|
||||
aux ((key, basis)::accu)
|
||||
with
|
||||
| Parsing.Parse_error -> List.rev accu
|
||||
in
|
||||
aux []
|
||||
|
4
Makefile
4
Makefile
@ -13,7 +13,9 @@ ALL_EXE=$(patsubst %.ml,%.native,$(wildcard qp_*.ml))
|
||||
|
||||
.PHONY: default
|
||||
|
||||
default: $(ALL_EXE)
|
||||
#default: $(ALL_EXE)
|
||||
default: test.byte
|
||||
|
||||
tests: $(ALL_TESTS)
|
||||
|
||||
qpackage.odocl: $(MLIFILES)
|
||||
|
@ -79,44 +79,48 @@ let to_long_string = function
|
||||
| Sb -> "Antimony" | Te -> "Tellurium" | I -> "Iodine"
|
||||
| Xe -> "Xenon" | Pt -> "Platinum"
|
||||
|
||||
|
||||
let to_int = function
|
||||
| X -> 0 | H -> 1 | He -> 2 | Li -> 3
|
||||
| Be -> 4 | B -> 5 | C -> 6 | N -> 7
|
||||
| O -> 8 | F -> 9 | Ne -> 10 | Na -> 11
|
||||
| Mg -> 12 | Al -> 13 | Si -> 14 | P -> 15
|
||||
| S -> 16 | Cl -> 17 | Ar -> 18 | K -> 19
|
||||
| Ca -> 20 | Sc -> 21 | Ti -> 22 | V -> 23
|
||||
| Cr -> 24 | Mn -> 25 | Fe -> 26 | Co -> 27
|
||||
| Ni -> 28 | Cu -> 29 | Zn -> 30 | Ga -> 31
|
||||
| Ge -> 32 | As -> 33 | Se -> 34 | Br -> 35
|
||||
| Kr -> 36 | Rb -> 37 | Sr -> 38 | Y -> 39
|
||||
| Zr -> 40 | Nb -> 41 | Mo -> 42 | Tc -> 43
|
||||
| Ru -> 44 | Rh -> 45 | Pd -> 46 | Ag -> 47
|
||||
| Cd -> 48 | In -> 49 | Sn -> 50 | Sb -> 51
|
||||
| Te -> 52 | I -> 53 | Xe -> 54 | Pt -> 78
|
||||
|
||||
|
||||
let to_charge c =
|
||||
begin
|
||||
match c with
|
||||
| X -> 0 | H -> 1 | He -> 2 | Li -> 3
|
||||
| Be -> 4 | B -> 5 | C -> 6 | N -> 7
|
||||
| O -> 8 | F -> 9 | Ne -> 10 | Na -> 11
|
||||
| Mg -> 12 | Al -> 13 | Si -> 14 | P -> 15
|
||||
| S -> 16 | Cl -> 17 | Ar -> 18 | K -> 19
|
||||
| Ca -> 20 | Sc -> 21 | Ti -> 22 | V -> 23
|
||||
| Cr -> 24 | Mn -> 25 | Fe -> 26 | Co -> 27
|
||||
| Ni -> 28 | Cu -> 29 | Zn -> 30 | Ga -> 31
|
||||
| Ge -> 32 | As -> 33 | Se -> 34 | Br -> 35
|
||||
| Kr -> 36 | Rb -> 37 | Sr -> 38 | Y -> 39
|
||||
| Zr -> 40 | Nb -> 41 | Mo -> 42 | Tc -> 43
|
||||
| Ru -> 44 | Rh -> 45 | Pd -> 46 | Ag -> 47
|
||||
| Cd -> 48 | In -> 49 | Sn -> 50 | Sb -> 51
|
||||
| Te -> 52 | I -> 53 | Xe -> 54 | Pt -> 78
|
||||
end
|
||||
|> Charge.of_int
|
||||
to_int c |> Charge.of_int
|
||||
|
||||
|
||||
let of_int = function
|
||||
| 0 -> X | 1 -> H | 2 -> He | 3 -> Li
|
||||
| 4 -> Be | 5 -> B | 6 -> C | 7 -> N
|
||||
| 8 -> O | 9 -> F | 10 -> Ne | 11 -> Na
|
||||
| 12 -> Mg | 13 -> Al | 14 -> Si | 15 -> P
|
||||
| 16 -> S | 17 -> Cl | 18 -> Ar | 19 -> K
|
||||
| 20 -> Ca | 21 -> Sc | 22 -> Ti | 23 -> V
|
||||
| 24 -> Cr | 25 -> Mn | 26 -> Fe | 27 -> Co
|
||||
| 28 -> Ni | 29 -> Cu | 30 -> Zn | 31 -> Ga
|
||||
| 32 -> Ge | 33 -> As | 34 -> Se | 35 -> Br
|
||||
| 36 -> Kr | 37 -> Rb | 38 -> Sr | 39 -> Y
|
||||
| 40 -> Zr | 41 -> Nb | 42 -> Mo | 43 -> Tc
|
||||
| 44 -> Ru | 45 -> Rh | 46 -> Pd | 47 -> Ag
|
||||
| 48 -> Cd | 49 -> In | 50 -> Sn | 51 -> Sb
|
||||
| 52 -> Te | 53 -> I | 54 -> Xe | 78 -> Pt
|
||||
| x -> raise (ElementError ("Element of charge "^(string_of_int x)^" unknown"))
|
||||
|
||||
|
||||
let of_charge c =
|
||||
match Charge.to_int c with
|
||||
| 0 -> X | 1 -> H | 2 -> He | 3 -> Li
|
||||
| 4 -> Be | 5 -> B | 6 -> C | 7 -> N
|
||||
| 8 -> O | 9 -> F | 10 -> Ne | 11 -> Na
|
||||
| 12 -> Mg | 13 -> Al | 14 -> Si | 15 -> P
|
||||
| 16 -> S | 17 -> Cl | 18 -> Ar | 19 -> K
|
||||
| 20 -> Ca | 21 -> Sc | 22 -> Ti | 23 -> V
|
||||
| 24 -> Cr | 25 -> Mn | 26 -> Fe | 27 -> Co
|
||||
| 28 -> Ni | 29 -> Cu | 30 -> Zn | 31 -> Ga
|
||||
| 32 -> Ge | 33 -> As | 34 -> Se | 35 -> Br
|
||||
| 36 -> Kr | 37 -> Rb | 38 -> Sr | 39 -> Y
|
||||
| 40 -> Zr | 41 -> Nb | 42 -> Mo | 43 -> Tc
|
||||
| 44 -> Ru | 45 -> Rh | 46 -> Pd | 47 -> Ag
|
||||
| 48 -> Cd | 49 -> In | 50 -> Sn | 51 -> Sb
|
||||
| 52 -> Te | 53 -> I | 54 -> Xe | 78 -> Pt
|
||||
| x -> raise (ElementError ("Element of charge "^(string_of_int x)^" unknown"))
|
||||
Charge.to_int c |> of_int
|
||||
|
||||
|
||||
let covalent_radius x =
|
||||
|
@ -1,6 +1,14 @@
|
||||
exception ElementError of string
|
||||
|
||||
type t
|
||||
type t =
|
||||
|X
|
||||
|H |He
|
||||
|Li|Be |B |C |N |O |F |Ne
|
||||
|Na|Mg |Al|Si|P |S |Cl|Ar
|
||||
|K |Ca|Sc|Ti|V |Cr|Mn|Fe|Co|Ni|Cu|Zn|Ga|Ge|As|Se|Br|Kr
|
||||
|Rb|Sr|Y |Zr|Nb|Mo|Tc|Ru|Rh|Pd|Ag|Cd|In|Sn|Sb|Te|I |Xe
|
||||
|Pt
|
||||
|
||||
|
||||
(** String conversion functions *)
|
||||
val of_string : string -> t
|
||||
@ -8,6 +16,8 @@ val to_string : t -> string
|
||||
val to_long_string : t -> string
|
||||
|
||||
(** Properties *)
|
||||
val to_int : t -> int
|
||||
val of_int : int -> t
|
||||
val to_charge : t -> Charge.t
|
||||
val of_charge : Charge.t -> t
|
||||
val covalent_radius : t -> Radius.t
|
||||
|
@ -1 +1,25 @@
|
||||
type xyz_input = string * ( (Element.t * (float array)) array)
|
||||
type coordinates = ( (Element.t * (float array)) array)
|
||||
|
||||
let of_xyz_file ~filename =
|
||||
let lexbuf =
|
||||
let ic = open_in filename in
|
||||
Lexing.from_channel ic
|
||||
in
|
||||
Xyz_parser.input Nuclei_lexer.read_all lexbuf
|
||||
|
||||
|
||||
let of_zmt_file ~filename =
|
||||
let ic = open_in filename in
|
||||
let rec aux accu =
|
||||
try
|
||||
let line = input_line ic in
|
||||
aux (line::accu)
|
||||
with End_of_file ->
|
||||
close_in ic;
|
||||
List.rev accu
|
||||
|> String.concat "\n"
|
||||
in aux []
|
||||
|> Zmatrix.of_string
|
||||
|> Zmatrix.to_xyz
|
||||
|> Array.map (fun (e,x,y,z) -> (e, [|x;y;z|]))
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
{
|
||||
open Nuclei_parser
|
||||
open Xyz_parser
|
||||
}
|
||||
|
||||
let eol = ['\n']
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* Parses basis sets in GAMESS format */
|
||||
/* Parses nuclear coordinates in xyz format */
|
||||
|
||||
%{
|
||||
exception InputError of string
|
||||
@ -11,19 +11,19 @@ exception InputError of string
|
||||
%token <float> FLOAT
|
||||
%token EOF
|
||||
|
||||
%start input_xyz
|
||||
%type <Nuclei.xyz_input> input_xyz
|
||||
%start input
|
||||
%type <(Element.t * (float array)) array> input
|
||||
|
||||
%% /* Grammar rules and actions follow */
|
||||
|
||||
input_xyz:
|
||||
input:
|
||||
| integer title atoms_xyz {
|
||||
let len = List.length $3 in
|
||||
if len <> $1 then
|
||||
let error_msg = Printf.sprintf "%d atoms entered, expected %d" len $1 in
|
||||
raise (InputError error_msg)
|
||||
else
|
||||
($2,Array.of_list $3)
|
||||
Array.of_list $3
|
||||
}
|
||||
|
||||
integer:
|
||||
@ -51,21 +51,8 @@ atoms_list:
|
||||
| { [] }
|
||||
| atoms_list WORD SPACE FLOAT SPACE FLOAT SPACE FLOAT EOL { (Element.of_string $2, [| $4;$6;$8 |]) :: $1 }
|
||||
| atoms_list WORD SPACE FLOAT SPACE FLOAT SPACE FLOAT SPACE EOL { (Element.of_string $2, [| $4;$6;$8 |]) :: $1 }
|
||||
|
||||
label:
|
||||
| FLOAT { Zmatrix.Value $1 }
|
||||
| WORD { Zmatrix.Label $1 }
|
||||
|
||||
first_line:
|
||||
| WORD { $1 }
|
||||
|
||||
second_line:
|
||||
| WORD INTEGER label { ($1,$2,$3) }
|
||||
|
||||
third_line:
|
||||
| WORD INTEGER label INTEGER label { ($1,$2,$3,$4,$5) }
|
||||
|
||||
nth_line:
|
||||
| WORD INTEGER label INTEGER label INTEGER label { ($1,$2,$3,$4,$5,$6,$7) }
|
||||
| atoms_list INTEGER SPACE FLOAT SPACE FLOAT SPACE FLOAT EOL { (Element.of_int $2, [| $4;$6;$8 |]) :: $1 }
|
||||
| atoms_list INTEGER SPACE FLOAT SPACE FLOAT SPACE FLOAT SPACE EOL { (Element.of_int $2, [| $4;$6;$8 |]) :: $1 }
|
||||
|
||||
|
||||
|
@ -200,20 +200,6 @@ let rotation_matrix axis angle =
|
||||
let apply_rotation_matrix rot u =
|
||||
(dot rot.(0) u, dot rot.(1) u, dot rot.(2) u)
|
||||
|
||||
let center_of_mass l =
|
||||
let (x,y,z) =
|
||||
let sum_mass, com =
|
||||
Array.fold_left (fun (s,com) (e,x,y,z) ->
|
||||
let mass =
|
||||
Positive_float.to_float @@ Element.mass e
|
||||
in
|
||||
(s +. mass, ( mass |. (x,y,z) ) |+ com) )
|
||||
(0., (0.,0.,0.)) l
|
||||
in
|
||||
(1. /. sum_mass) |. com
|
||||
in
|
||||
Printf.printf "%f %f %f\n" x y z ; (x,y,z)
|
||||
|
||||
let to_xyz (z,map) =
|
||||
let result =
|
||||
Array.make (Array.length z) None
|
||||
@ -300,14 +286,16 @@ let to_xyz (z,map) =
|
||||
| Some x -> x
|
||||
| None -> failwith "Some atoms were not defined" ) result
|
||||
in
|
||||
Array.to_list result
|
||||
result
|
||||
|
||||
|
||||
let to_xyz_string (l,map) =
|
||||
String.concat "\n"
|
||||
( to_xyz (l,map)
|
||||
|> List.map (fun (e,x,y,z) ->
|
||||
Printf.sprintf "%s %f %f %f\n" (Element.to_string e) x y z) )
|
||||
|> Array.map (fun (e,x,y,z) ->
|
||||
Printf.sprintf "%s %f %f %f\n" (Element.to_string e) x y z)
|
||||
|> Array.to_list
|
||||
)
|
||||
|
||||
|
||||
|
||||
|
@ -1,7 +1,22 @@
|
||||
type units =
|
||||
| Bohr
|
||||
| Angstrom
|
||||
;;
|
||||
|
||||
type angle_units =
|
||||
| Degree
|
||||
| Radian
|
||||
|
||||
let pi = acos (-1.)
|
||||
|
||||
let to_degree x =
|
||||
assert (x <= 2.*.pi);
|
||||
assert (x >= -2.*.pi);
|
||||
x *. 180. /. pi
|
||||
|
||||
let to_radian x =
|
||||
assert (x <= 360.);
|
||||
assert (x >= -360.);
|
||||
x *. pi /. 180.
|
||||
|
||||
let angstrom_to_bohr = 1. /. 0.52917721092
|
||||
let bohr_to_angstrom = 0.52917721092
|
||||
|
@ -1,7 +1,8 @@
|
||||
type units = Bohr | Angstrom
|
||||
type units = Bohr | Angstrom
|
||||
type angle_units = Degree | Radian
|
||||
|
||||
val to_radian : float -> float
|
||||
val to_degree : float -> float
|
||||
|
||||
(** Conversion functions *)
|
||||
val angstrom_to_bohr : float
|
||||
val bohr_to_angstrom : float
|
||||
|
||||
|
||||
|
73
Utils/Util.ml
Normal file
73
Utils/Util.ml
Normal file
@ -0,0 +1,73 @@
|
||||
(** Constants *)
|
||||
let pi = acos (-1.)
|
||||
let pi_inv = 1. /. pi
|
||||
let two_over_sq_pi = 2. /. (sqrt pi)
|
||||
let factmax = 150
|
||||
|
||||
|
||||
(** Generalized Boys function. Uses GSL's incomplete Gamma function.
|
||||
maxm : Maximum total angular momentum
|
||||
*)
|
||||
let boys_function ~maxm t =
|
||||
begin
|
||||
if t = 0. then
|
||||
Array.init (maxm+1) (fun m -> 1. /. float_of_int (m+m+1))
|
||||
else
|
||||
let incomplete_gamma ~alpha x =
|
||||
Gsl.Sf.gamma alpha *. ( Gsl.Sf.gamma_inc_P alpha x )
|
||||
in
|
||||
let t_inv =
|
||||
1. /. t
|
||||
in
|
||||
let factor =
|
||||
Array.make (maxm+1) (0.5, sqrt t_inv);
|
||||
in
|
||||
for i=1 to maxm
|
||||
do
|
||||
let (dm, f) = factor.(i-1) in
|
||||
factor.(i) <- (dm +. 1., f *. t_inv);
|
||||
done;
|
||||
Array.map (fun (dm, f) -> (incomplete_gamma dm t ) *. 0.5 *. f) factor
|
||||
end
|
||||
|
||||
|
||||
|
||||
let fact_memo =
|
||||
let rec aux accu_l accu = function
|
||||
| 0 -> aux [1.] 1. 1
|
||||
| i when (i = factmax) ->
|
||||
let x = (float_of_int factmax) *. accu in
|
||||
List.rev (x::accu_l)
|
||||
| i -> let x = (float_of_int i) *. accu in
|
||||
aux (x::accu_l) x (i+1)
|
||||
in
|
||||
aux [] 0. 0
|
||||
|> Array.of_list
|
||||
|
||||
|
||||
|
||||
(** Factorial function.
|
||||
@raise Invalid_argument for negative or arguments >100. *)
|
||||
let fact = function
|
||||
| i when (i < 0) ->
|
||||
raise (Invalid_argument "Argument of factorial should be non-negative")
|
||||
| i when (i > 150) ->
|
||||
raise (Invalid_argument "Result of factorial is infinite")
|
||||
| i -> fact_memo.(i)
|
||||
|
||||
|
||||
|
||||
(** Integer powers of floats *)
|
||||
let rec pow a = function
|
||||
| 0 -> 1.
|
||||
| 1 -> a
|
||||
| 2 -> a *. a
|
||||
| 3 -> a *. a *. a
|
||||
| -1 -> 1. /. a
|
||||
| n when (n<0) -> pow (1./.a) (-n)
|
||||
| n ->
|
||||
let b = pow a (n / 2) in
|
||||
b *. b *. (if n mod 2 = 0 then 1. else a)
|
||||
;;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user