To receive notifications about scheduled maintenance, please subscribe to the mailing-list gitlab-operations@sympa.ethz.ch. You can subscribe to the mailing-list at https://sympa.ethz.ch

Commit aaec79ae authored by psd's avatar psd
Browse files

Exercise 8

parent b95a4bfe
{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"metadata": {},
"outputs": [],
"source": [
"import numpy as np\n",
"import matplotlib.pyplot as plt\n",
"\n",
"from ase import Atoms\n",
"from ase.io import read,write\n",
"from ase.visualize import view\n",
"import nglview"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Tasks\n",
"\n",
"### Task 1\n",
"\n",
"Let's begin with some theory. The energy of system of atoms is:\n",
"\n",
"$H = \\sum_i p_i/2m_i + VR_i$.\n",
"\n",
"Expanding $V$ around equilibrium ($\\sum_i\\partial{V}/\\partial{R_i}=0$):\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\sum_{ij} \\frac{\\partial{V}}{\\partial{R_i}\\partial{R_j}}\\Delta R_i\\Delta R_j$\n",
"\n",
"which, in matrix form reads:\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{P_{3N}\\}\\begin{bmatrix}{M_i}^{-1} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}\\{P_{3N}\\}^T + \n",
"\\frac{1}{2}\\{\\Delta R_{3N}\\}\\begin{bmatrix}{k_{ij}} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}\\{\\Delta R_{3N}\\}^T$\n",
"\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{P_i(\\sqrt{M_i})^{-1}\\}\\{P_i(\\sqrt{M_i})^{-1}\\}^T + \n",
"\\frac{1}{2}\\{\\Delta R_i(\\sqrt{M_i})^{-1}\\}\\underbrace{\\begin{bmatrix}{k_{ij}(\\sqrt{M_iM_j})^{-1}} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}}_{\\text{Hessian matrix}}\\{\\Delta R_i(\\sqrt{M_i})^{-1}\\}^T$\n",
"\n",
"In the basis basis states of the Hessian matrix, the above equation can be written:\n",
"\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{\\pi_i\\}\\{\\pi_i\\}^T + \n",
"\\frac{1}{2}\\{\\delta\\rho_i\\}\\begin{bmatrix}{\\omega_i} &&\\\\ &\\ddots& \\\\ &&\\\\ \\end{bmatrix}\\{\\delta\\rho_i\\}^T$\n",
"\n",
"\n",
"where ${\\delta\\rho_i},{\\pi_i}$ are the mass normalized position and momentum vectors. The above equation corresponds to a set of **uncoupled harmonic oscillators**:\n",
"\n",
"$\\boxed{H = V_0 + \\frac{1}{2}\\sum_{\\alpha} \\Big( \\frac{\\pi_{\\alpha}^2}{2} + \\frac{\\omega_{\\alpha}2}{2}\\rho_{\\alpha}^2 \\Big)}$\n",
"\n",
"The **molden** file contains the eigenvalues and eigenvectors of the Hessian matrix. The eigenvectros corresponds to the atomic displacements and the eigenvalues are the vibrational frequencies. Your task is to devise a method to display the vibrational modes, making use of the *vibr_displacements* and *atoms*(ase.Atoms object) returned by the function *read_molden*. \n",
"\n",
"For the purpose, complete the skeleton function *get_trajectory*, which is initialized in a cell below, and make use of the ase.Atoms class, which is initialized with a list of atomic elements and their respective coordinates. \n",
"\n",
"**Hint**: Write the equation of motion (Lagrangian) for the equation above and find the time evolution of the atoms for a given normal mode."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Task 2\n",
"- Compare the vibrational frequencies of methanol with experiments (see paper) and the one of benzene with literature on the internet.\n",
"- Which kind of modes will correspond to stretching of CH and CC bonds?\n",
"- Try to animate some frequencies, and report the kind of mode corresponding to all peaks.\n",
"- In the methanol case, you can compare the result you obtained with the one with better basis set and convergence. \n",
"- Examine the differences between the file vib.c6h6.inp and the vib.c6h6.ref, and the difference in spectra. Discuss."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Funcitons:\n",
"\n",
"**read_molden(file):**\n",
"\n",
" input: \n",
" file - molden filename\n",
" return:\n",
" atoms - ase.Atom object\n",
" frequency - vibrational frequencies\n",
" vibr_displacements - vibrational atomic displacements in Angstrom \n",
" \n",
"**get_trajectory(mode):**\n",
"\n",
" input:\n",
" mode - mode number\n",
" return:\n",
" trajectory - trajectory of atomic displacements for specified mode "
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {},
"outputs": [],
"source": [
"def read_molden(file):\n",
" \n",
" with open(file) as f:\n",
" data = f.readlines()\n",
"\n",
" freq = []\n",
" info_atoms = [] # element, x, y, z\n",
" vibr_displacements = [] # [vibration_nr][coord]\n",
"\n",
" inten = []\n",
"\n",
"\n",
" section = ''\n",
" b2A=0.52917721067\n",
" # Parse the datafile\n",
" for line in data:\n",
" line = line.strip()\n",
"\n",
" # Are we entering into a new section?\n",
" if line[0] == '[':\n",
" section = line.strip('[]').lower()\n",
" continue\n",
"\n",
" if section == 'freq':\n",
" freq.append(float(line))\n",
"\n",
" if section == 'fr-coord':\n",
" el, x, y, z = line.split()\n",
" info_atoms.append([el, float(x)*b2A, float(y)*b2A, float(z)*b2A])\n",
"\n",
" if section == 'fr-norm-coord':\n",
" if line.startswith('vibration'):\n",
" vibr_displacements.append([])\n",
" continue\n",
" coords = [float(x) for x in line.split()]\n",
" vibr_displacements[-1].append(coords)\n",
"\n",
" if section == 'int':\n",
" inten.append(float(line))\n",
"\n",
" vibr_displacements = np.asanyarray(vibr_displacements)\n",
" info_atoms = np.asanyarray(info_atoms)\n",
" atoms = Atoms(info_atoms[:,0], info_atoms[:,1:4])\n",
"\n",
" return atoms, freq, vibr_displacements"
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {},
"outputs": [],
"source": [
"def get_trajectory(mode):\n",
" '''\n",
" TODO: Solve the equation of motion and complete the missing ___ \n",
" '''\n",
" trajectory = []\n",
" for time in time_arr:\n",
" vibr_atoms = Atoms(a.get_chemical_symbols(), a.positions+'''___''')\n",
" trajectory.append(vibr_atoms)\n",
" return trajectory"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Read molden file "
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {},
"outputs": [],
"source": [
"file = \"./C6H6-VIBRATIONS-1.ref.mol\"\n",
"a, freq, vibr_displacements = read_molden(file)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## View atoms at equilibrium"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {},
"outputs": [
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "e2d2a73120ff458f8f0a89ad84291be5",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"NGLWidget()"
]
},
"metadata": {},
"output_type": "display_data"
}
{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"metadata": {},
"outputs": [],
"source": [
"import numpy as np\n",
"import matplotlib.pyplot as plt\n",
"\n",
"from ase import Atoms\n",
"from ase.io import read,write\n",
"from ase.visualize import view\n",
"import nglview"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Tasks\n",
"\n",
"### Task 1\n",
"\n",
"Let's begin with some theory. The energy of system of atoms is:\n",
"\n",
"$H = \\sum_i p_i/2m_i + VR_i$.\n",
"\n",
"Expanding $V$ around equilibrium ($\\sum_i\\partial{V}/\\partial{R_i}=0$):\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\sum_{ij} \\frac{\\partial{V}}{\\partial{R_i}\\partial{R_j}}\\Delta R_i\\Delta R_j$\n",
"\n",
"which, in matrix form reads:\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{P_{3N}\\}\\begin{bmatrix}{M_i}^{-1} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}\\{P_{3N}\\}^T + \n",
"\\frac{1}{2}\\{\\Delta R_{3N}\\}\\begin{bmatrix}{k_{ij}} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}\\{\\Delta R_{3N}\\}^T$\n",
"\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{P_i(\\sqrt{M_i})^{-1}\\}\\{P_i(\\sqrt{M_i})^{-1}\\}^T + \n",
"\\frac{1}{2}\\{\\Delta R_i(\\sqrt{M_i})^{-1}\\}\\underbrace{\\begin{bmatrix}{k_{ij}(\\sqrt{M_iM_j})^{-1}} &&\\\\ && \\\\ &&\\\\ \\end{bmatrix}}_{\\text{Hessian matrix}}\\{\\Delta R_i(\\sqrt{M_i})^{-1}\\}^T$\n",
"\n",
"In the basis basis states of the Hessian matrix, the above equation can be written:\n",
"\n",
"\n",
"$H = V_0 + \\frac{1}{2}\\{\\pi_i\\}\\{\\pi_i\\}^T + \n",
"\\frac{1}{2}\\{\\delta\\rho_i\\}\\begin{bmatrix}{\\omega_i} &&\\\\ &\\ddots& \\\\ &&\\\\ \\end{bmatrix}\\{\\delta\\rho_i\\}^T$\n",
"\n",
"\n",
"where ${\\delta\\rho_i},{\\pi_i}$ are the mass normalized position and momentum vectors. The above equation corresponds to a set of **coupled harmonic hoscillators**:\n",
"\n",
"$\\boxed{H = V_0 + \\frac{1}{2}\\sum_{\\alpha} \\Big( \\frac{\\pi_{\\alpha}^2}{2} + \\frac{\\omega_{\\alpha}2}{2}\\rho_{\\alpha}^2 \\Big)}$\n",
"\n",
"The **molden** file contains the eigenvalues and eigenvectors of the Hessian matrix. The eigenvectros corresponds to the atomic displacements and the eigenvalues are the vibrational frequencies. Your task is to devise a method to display the vibrational modes, making use of the *vibr_displacements* and *atoms*(ase.Atoms object) return by the function *read_molden*. \n",
"\n",
"For the purpose, complete the skeleton function *get_trajectory*, which is initialized in a cell below, and make use of the ase.Atoms class, which is initialized with a list of atomic elements and their respective coordinates. \n",
"\n",
"**Hint**: Write the equation of motion (Lagrangian) for the equation above and find the time evolution of the atoms for a given normal mode."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Task 2\n",
"- Compare the vibrational frequencies of methanol with experiments (see paper) and the one of benzene with literature on the internet.\n",
"- Which kind of modes will correspond to stretching of CH and CC bonds?\n",
"- Try to animate some frequencies, and report the kind of mode corresponding to all peaks.\n",
"- In the methanol case, you can compare the result you obtained with the one with better basis set and convergence. \n",
"- Examine the differences between the file vib.c6h6.inp and the vib.c6h6.ref, and the difference in spectra. Discuss."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Funcitons:\n",
"\n",
"**read_molden(file):**\n",
"\n",
" input: \n",
" file - molden filename\n",
" return:\n",
" atoms - ase.Atom object\n",
" frequency - vibrational frequencies\n",
" vibr_displacements - vibrational atomic displacements in Angstrom \n",
" \n",
"**get_trajectory(mode):**\n",
"\n",
" input:\n",
" mode - mode number\n",
" return:\n",
" trajectory - trajectory of atomic displacements for specified mode "
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {},
"outputs": [],
"source": [
"def read_molden(file):\n",
" \n",
" with open(file) as f:\n",
" data = f.readlines()\n",
"\n",
" freq = []\n",
" info_atoms = [] # element, x, y, z\n",
" vibr_displacements = [] # [vibration_nr][coord]\n",
"\n",
" inten = []\n",
"\n",
"\n",
" section = ''\n",
" b2A=0.52917721067\n",
" # Parse the datafile\n",
" for line in data:\n",
" line = line.strip()\n",
"\n",
" # Are we entering into a new section?\n",
" if line[0] == '[':\n",
" section = line.strip('[]').lower()\n",
" continue\n",
"\n",
" if section == 'freq':\n",
" freq.append(float(line))\n",
"\n",
" if section == 'fr-coord':\n",
" el, x, y, z = line.split()\n",
" info_atoms.append([el, float(x)*b2A, float(y)*b2A, float(z)*b2A])\n",
"\n",
" if section == 'fr-norm-coord':\n",
" if line.startswith('vibration'):\n",
" vibr_displacements.append([])\n",
" continue\n",
" coords = [float(x) for x in line.split()]\n",
" vibr_displacements[-1].append(coords)\n",
"\n",
" if section == 'int':\n",
" inten.append(float(line))\n",
"\n",
" vibr_displacements = np.asanyarray(vibr_displacements)\n",
" embed()\n",
" info_atoms = np.asanyarray(info_atoms)\n",
" atoms = Atoms(info_atoms[:,0], info_atoms[:,1:4])\n",
"\n",
" return atoms, freq, vibr_displacements"
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {},
"outputs": [],
"source": [
"def get_trajectory(mode):\n",
" enhance_disp = 2.0\n",
" time_arr = np.linspace(0.0, 2*np.pi, 20)\n",
"\n",
" trajectory = []\n",
" for time in time_arr:\n",
" #eq_atoms = ase.Atoms(len(chem_symbols)*['O'], eq_coords)\n",
" vibr_atoms = Atoms(a.get_chemical_symbols(), a.positions+enhance_disp*np.sin(time)*vibr_displacements[mode])\n",
" trajectory.append(vibr_atoms)\n",
" return trajectory"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Read molden file "
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Python 3.7.1 (default, Dec 14 2018, 19:28:38) \n",
"Type 'copyright', 'credits' or 'license' for more information\n",
"IPython 7.2.0 -- An enhanced Interactive Python. Type '?' for help.\n",
"\n",
"In [1]: info_atoms\n",
"Out[1]: \n",
"[['C', 2.222544284814e-05, 1.396857970284175, 0.0],\n",
" ['H', -1.2171075845410001e-05, 2.487163053250008, -0.0],\n",
" ['C', -1.210924148834321, 0.6987107720067693, -0.0],\n",
" ['H', -2.1548170103291895, 1.2443078223466488, 0.0],\n",
" ['C', -1.2109310281380596, -0.6986636752350197, 0.0],\n",
" ['H', -2.154787376405392, -1.2443226393085474, -0.0],\n",
" ['C', -2.169626563747e-05, -1.396875433132127, -0.0],\n",
" ['H', 1.2171075845410001e-05, -2.4871815744523817, 0.0],\n",
" ['C', 1.210909861049633, -0.6987023051713985, 0.0],\n",
" ['H', 2.1548021933672907, -1.244299355511278, 0.0],\n",
" ['C', 1.2109463742771691, 0.6986721420703903, -0.0],\n",
" ['H', 2.1548048392533437, 1.2443311061439182, 0.0]]\n",
"\n",
"In [2]: exit\n",
"\n"
]
}
],
"source": [
"file = \"./C6H6-VIBRATIONS-1.ref.mol\"\n",
"a, vibr_displacements = read_molden(file)"
This diff is collapsed.
[Molden Format]
[FREQ]
400.302903
401.555638
596.097032
602.918089
661.189688
706.249913
833.568431
833.756231
949.504594
949.976122
976.963838
985.823710
993.020931
1029.977506
1035.062465
1143.899937
1163.645030
1165.969536
1338.887202
1347.664359
1466.711983
1471.797438
1593.030396
1594.117474
3087.283723
3096.781439
3097.757885
3111.829664
3112.819108
3121.735327
[FR-COORD]
C 0.000042 2.639679 0.000000
H -0.000023 4.700057 -0.000000
C -2.288315 1.320372 -0.000000
H -4.072014 2.351401 0.000000
C -2.288328 -1.320283 0.000000
H -4.071958 -2.351429 -0.000000
C -0.000041 -2.639712 -0.000000
H 0.000023 -4.700092 0.000000
C 2.288288 -1.320356 0.000000
H 4.071986 -2.351385 0.000000
C 2.288357 1.320299 -0.000000
H 4.071991 2.351445 0.000000
[FR-NORM-COORD]
vibration 1
-0.000005 0.000033 0.000502
0.000008 0.000052 0.001115
-0.000006 -0.000005 0.201939
-0.000014 -0.000001 0.456716
0.000029 -0.000003 -0.202439
0.000029 0.000023 -0.457874
-0.000000 -0.000010 0.000502
-0.000007 -0.000001 0.001115
-0.000015 -0.000015 0.201939
-0.000009 0.000004 0.456736
-0.000005 -0.000005 -0.202439
0.000013 -0.000022 -0.457854
vibration 2
-0.000012 0.000028 0.233236
0.000011 0.000041 0.528255
0.000003 -0.000006 -0.117066
-0.000001 -0.000018 -0.264924
0.000024 0.000003 -0.116197
0.000027 0.000024 -0.262997
-0.000004 -0.000007 0.233236
-0.000007 0.000001 0.528231
-0.000005 -0.000015 -0.117065
-0.000000 -0.000012 -0.264935
-0.000010 -0.000006 -0.116197
0.000001 -0.000016 -0.262993
vibration 3
-0.000042 0.357385 -0.000048
0.000111 0.355791 0.000060
0.224264 0.024295 -0.000010
0.058038 -0.261826 -0.000001
0.224428 -0.024164 0.000061
0.058276 0.261838 -0.000101
0.000053 -0.357363 -0.000019
-0.000009 -0.355772 -0.000057
-0.224283 -0.024294 -0.000027
-0.058128 0.261748 0.000037
-0.224421 0.024148 0.000033
-0.058266 -0.261852 0.000170
vibration 4
-0.151123 -0.000115 -0.000032
0.231673 -0.000110 -0.000092
-0.232074 0.220707 0.000016
-0.325667 0.056506 0.000006
0.231918 0.220718 0.000016
0.325563 0.056426 -0.000152
0.151125 0.000103 0.000009
-0.231598 0.000084 -0.000037
0.232078 -0.220697 -0.000015
0.325650 -0.056526 -0.000118
-0.231927 -0.220715 0.000036
-0.325603 -0.056390 0.000042
vibration 5
0.000011 0.000006 -0.034007
0.000015 0.000015 0.406053
-0.000017 0.000015 -0.034214
-0.000033 0.000015 0.407191
-0.000007 -0.000008 -0.034184
-0.000006 -0.000030 0.407242
0.000014 0.000002 -0.034041
0.000007 0.000007 0.406001
0.000009 -0.000003 -0.034180
0.000006 0.000002 0.407241
-0.000009 -0.000011 -0.034216
-0.000007 -0.000026 0.407180
vibration 6
-0.000010 0.000006 0.201113
0.000012 0.000009 0.356838
-0.000011 0.000016 -0.201393
-0.000026 -0.000015 -0.354372
0.000018 0.000010 0.201408
0.000023 -0.000002 0.354173
0.000008 -0.000002 -0.201095
-0.000016 0.000000 -0.357067
0.000008 -0.000018 0.201412
0.000021 0.000012 0.354145
-0.000013 -0.000013 -0.201388
-0.000016 0.000001 -0.354400
vibration 7
-0.000006 0.000021 -0.000410
-0.000022 0.000024 0.002727
0.000002 0.000001 -0.074048
-0.000015 -0.000024 0.495897
0.000005 0.000003 -0.073645
0.000009 0.000001 0.493120
-0.000008 -0.000019 0.000410
-0.000006 -0.000020 -0.002735
0.000004 -0.000014 0.074048
0.000024 0.000005 -0.495875
0.000004 0.000007 0.073647
0.000007 0.000018 -0.493151
vibration 8
-0.000002 0.000013 0.085376
0.000002 0.000012 -0.569602
0.000000 -0.000006 0.042262
-0.000014 -0.000024 -0.284524
0.000029 -0.000002 -0.042966
0.000034 0.000006 0.289248
-0.000001 0.000010 -0.085378
-0.000010 0.000026 0.569633
-0.000020 -0.000008 -0.042260
-0.000023 -0.000004 0.284498
-0.000007 -0.000008 0.042966
0.000008 -0.000026 -0.289260
vibration 9
0.000007 -0.000075 -0.000041
0.000025 -0.000107 0.000235
0.000077 0.000027 0.093256
0.000136 0.000100 -0.491336
-0.000032 0.000025 -0.093220
-0.000099 0.000109 0.491130
0.000011 -0.000037 -0.000038
0.000034 -0.000052 0.000217
0.000020 0.000039 0.093259
0.000107 0.000179 -0.491352
-0.000086 -0.000006 -0.093215
-0.000163 0.000102 0.491102
vibration 10
-0.000022 0.000049 -0.107841
-0.000062 0.000065 0.567904
0.000013 -0.000046 0.053798
-0.000017 -0.000105 -0.282730
0.000008 -0.000010 0.053867
0.000035 -0.000018 -0.283113
-0.000023 0.000062 -0.107833
-0.000078 0.000071 0.567853
0.000017 -0.000034 0.053798
-0.000037 -0.000137 -0.282724
0.000016 -0.000008 0.053868
0.000038 -0.000031 -0.283120
vibration 11
0.000005 0.000014 0.060002
0.000021 0.000013 -0.405291
-0.000004 0.000009 -0.059689
0.000022 0.000065 0.403104
-0.000042 -0.000015 0.059691
-0.000060 0.000020 -0.403115
0.000002 -0.000028 -0.060007
0.000019 -0.000037 0.405315
0.000033 0.000002 0.059694
0.000041 0.000003 -0.403133
0.000003 0.000011 -0.059690
-0.000008 0.000022 0.403106
vibration 12