Skip to content

Commit

Permalink
New version 1.1
Browse files Browse the repository at this point in the history
  • Loading branch information
rubel75 committed Jan 2, 2014
1 parent 6318cee commit 34b5f3d
Show file tree
Hide file tree
Showing 9 changed files with 1,175 additions and 939 deletions.
1,239 changes: 591 additions & 648 deletions berrypi

Large diffs are not rendered by default.

569 changes: 349 additions & 220 deletions calculations.py

Large diffs are not rendered by default.

4 changes: 2 additions & 2 deletions config.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,10 @@
#######################################################

#fix for location of python file locations when executing from the python commandline
DEFAULT_BIN_PATH=''
DEFAULT_BIN_PATH='/home/oleg/BerryPItest/'

#Fix for python path to make sure it grabs the latest version
DEFAULT_PYTHON_PATH=''
DEFAULT_PYTHON_PATH='/home/oleg/.local/bin/python2.7'

########################################################
####Some default values for the automation of each case
Expand Down
17 changes: 17 additions & 0 deletions convunits.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
'''
File provide some usefull conversions for units, such as
[Bohr] => [m] and so on
'''

import math

# [Bohr] => [m]
def bohrToMeters(value, dimension = 1):
BOHR_CONSTANT = 5.2917725e-11
return value * ((BOHR_CONSTANT) ** dimension)


if __name__ == "__main__":
print 'This program is not intended for execution'
print 'Load it as a module instead'
print 'import convunits'
81 changes: 55 additions & 26 deletions mmn2pathphase.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,9 @@
import sys
import numpy

#VERBOSE = True
VERBOSE = False # Whether or not to print extra info

### case.win parsing
parse_line_list = lambda line, delimiter, T : [T(y) for y in [x.strip() for x in line.strip().split(delimiter)] if y]

def parse_win_mp_grid(f):
parse_line_list = lambda line, delimiter, T : [T(y) for y in [x.strip() for x in line.strip().split(delimiter)] if y]
for line in f.xreadlines():
if 'mp_grid' in line:
# mp_grid : A B C
Expand Down Expand Up @@ -143,47 +139,65 @@ def wrap_vector(v,d,D):
return nnkpts, neighbour_graph

def print_usage():
print >> sys.stderr, "Usage: {0} case [direction]".format(sys.argv[0])
print >> sys.stderr, "Usage: mmn2pathphase case [direction]"
print >> sys.stderr, " direction x, y, or z; for <x, y, z> (default x)"

###############################################################################

###############################################################################
# Begin MAIN
###############################################################################

if __name__ == "__main__":
def main(args):

if len(sys.argv) < 2:
#VERBOSE = True
VERBOSE = False # Whether or not to print extra info

### case.win parsing
parse_line_list = lambda line, delimiter, T : [T(y) for y in [x.strip() for x in line.strip().split(delimiter)] if y]

if len(args) < 2:
print >> sys.stderr, "Error: no case provided"
exit(1)

spOption = '' # no spin polarization by default
soOption = '' # no spin-orbit by default
for arg in args: # check for spin polarization in arguments
if arg == '-up':
spOption = 'up'
elif arg == '-dn':
spOption = 'dn'
elif arg == '-so':
spOption = 'up' # keep up spin for spin-orbit ('dn' should not make a difference)
soOption = 'so'

# Get case name from arguments
case_name = sys.argv[1]
case_name = args[0]

# Get direction from arguments
direction_args = {'x': [1, 0, 0],
'y': [0, 1, 0],
'z': [0, 0, 1]}

if len(sys.argv) > 2:
if not direction_args.has_key(sys.argv[2]):
print >> sys.stderr, "Error: unknown direction '{0}'".format(sys.argv[2])
if len(args) > 2:
if not direction_args.has_key(args[1]):
print >> sys.stderr, "Error: unknown direction '{0}'".format(args[1])
exit(1)

direction = direction_args[sys.argv[2]]
direction = direction_args[args[1]]
else:
direction = direction_args['x']

# Initialize some lists
phases = {} # for index k, the phase between k and its neighbour along the specified direction
phase_sums = [] # for index k, the accumulated phase along the path in the specified direction starting at k

# Get information from case.win
f_win = open(case_name + '.win', 'r')
dimensions = parse_win_mp_grid(f_win)
# Get k-mesh information from case.win
f_win = open(case_name + '.win' + spOption, 'r')
kmesh = parse_win_mp_grid(f_win)
f_win.close()

# Calculate the neighbours of interest
nnkpts, neighbour_graph = determine_neighbours(dimensions, direction, [2, 1, 0])
nnkpts, neighbour_graph = determine_neighbours(kmesh, direction, [2, 1, 0])
# > we need the pairs list (nnkpts) to discriminate values found in the
# case.mmn file
# > we need the neighbour graph (neighbour_graph) in order to find the sum
Expand All @@ -192,8 +206,12 @@ def print_usage():
if VERBOSE:
print nnkpts

# Open file containing Mmn data (case.mmn)
f_mmn = open(case_name + '.mmn', 'r')
# Open file containing Mmn data (case.mmn)
if soOption == 'so':
opt = 'so' # file *.mmnso in case of spin-orbit
else:
opt = spOption # file *.mmn(up/dn) for SP case without SO
f_mmn = open(case_name + '.mmn' + opt, 'r')
f_mmn.readline() # Ignore first line

n_energy, n_pairs, n_neighbours = parse_mmn_info_line(f_mmn.readline())
Expand All @@ -219,15 +237,16 @@ def print_usage():
# Put value into matrix
pair_matrix[a, b] = element_value

# Determine the phase between the pair from the matrix determinant
# Determine the phase between the pair from the matrix determinant
det_Mmn = numpy.linalg.det(pair_matrix)
phases[k1] = numpy.angle(det_Mmn)

if VERBOSE:
print (k1, k2, G)
print pair_matrix
print det_Mmn
print numpy.angle(det_Mmn)
print "(k1, k2, G)=", (k1, k2, G)
print "pair_matrix Mmn=", pair_matrix
print "eig(pair_matrix)=", numpy.linalg.eig(pair_matrix)[0]
print "det_Mmn=", det_Mmn
print "numpy.angle(det_Mmn)=", numpy.angle(det_Mmn)
print '---'
else:
if VERBOSE:
Expand Down Expand Up @@ -270,7 +289,7 @@ def print_usage():
phase_sums.sort(key=lambda x:x[0]) # TODO use sorted

# Write out path phases
f_pathphase = open(case_name + '.pathphase', 'w')
f_pathphase = open(case_name + '.pathphase' + spOption, 'w')

# Write out number of paths
f_pathphase.write('%4d\n' % len(phase_sums))
Expand All @@ -284,6 +303,16 @@ def print_usage():

f_pathphase.close()

return phase_sums

###############################################################################
# end MAIN
###############################################################################

if __name__ == "__main__":

main(sys.argv[1:]) # path all arguments except for the first one

###############################################################################

###############################################################################
160 changes: 132 additions & 28 deletions parsing.py
Original file line number Diff line number Diff line change
Expand Up @@ -212,14 +212,128 @@ def parse(self):
raise ParseError("ERROR: Missing data in *.outputd file", MissingTags)


# THIS IS THE ORIGINAL CLASS (Sat 09 Nov 2013 06:27:43 PM CST)
#class MainSCFParser(AbstractParser):
# def parse(self):
# tempText = self.getFileContent()
#
# tagList = [
# re.compile(r':BAN[0-9]+'),
# re.compile(r':VOL'),
# re.compile(r':ITE(?P<num>[0-9]+)'),
# ]
# #strip out all of the iterations, volume and band lines
# theText = []
# for line in tempText:
# for tag in tagList:
# if tag.search(line):
# theText.append(line)
#
# #grab the last iteration
# theIterationIndex, theIterationNumber = 0,0
# for number, line in enumerate(theText):
# result_theIterationNum = tagList[2].search(line) #ITE regex
# if result_theIterationNum:
# theIterationNumber = int(result_theIterationNum.group('num'))
# theIterationIndex = number
# #i'm assuming the last one it finds is the last iteration
#
# #delete up to the last iteration
# theText = theText[theIterationIndex:]
#
# re_volumeSize = re.compile(r':VOL +: +UNIT CELL VOLUME = +(?P<cellVolume>[0-9.]+)')
# re_bandListing = re.compile(r':BAN[0-9]+: +(?P<bandNum>[0-9]+) +[0-9.-]+ +[0-9.-]+ +(?P<occupancy>[0-9.]+)')
#
# self['Band List'] = []
# for line in theText:
# #volume
# result_volumeSize = re_volumeSize.search(line)
# if result_volumeSize:
# self['Cell Volume'] = float(result_volumeSize.group('cellVolume'))

# #band listings
# result_bandListing = re_bandListing.search(line)
# if result_bandListing:
# theDict = {
# 'band range' : int(result_bandListing.group('bandNum')),
# 'occupancy' : int(float(result_bandListing.group('occupancy'))),
# }
# self['Band List'].append(theDict)
# MissingTags = checkForTags(self, [
# 'Cell Volume',
# ])
# # if missing any tags, or have nothing within the band list
# if MissingTags:
# raise ParseError("ERROR: Missing data in *.scf file", MissingTags)
# if not self['Band List']:
# raise ParseError('ERROR: Missing band list in *.scf file', ())

#class MainSCFParser(AbstractParser):
# def parse(self):
# tempText = self.getFileContent()
#
# tagList = [
# re.compile(r':BAN[0-9]+'),
# re.compile(r':VOL'),
# re.compile(r':ITE(?P<num>[0-9]+)'),
# ]
# #strip out all of the iterations, volume and band lines
# theText = []
# for line in tempText:
# for tag in tagList:
# if tag.search(line):
# theText.append(line)
#
# #grab the last iteration
# theIterationIndex, theIterationNumber = 0,0
# for number, line in enumerate(theText):
# result_theIterationNum = tagList[2].search(line) #ITE regex
# if result_theIterationNum:
# theIterationNumber = int(result_theIterationNum.group('num'))
# theIterationIndex = number
# #i'm assuming the last one it finds is the last iteration
#
# #delete up to the last iteration
# theText = theText[theIterationIndex:]
#
# re_volumeSize = re.compile(r':VOL +: +UNIT CELL VOLUME = +(?P<cellVolume>[0-9.]+)')
# re_bandListing = re.compile(r':BAN[0-9]+: +(?P<bandNum>[0-9]+) +[0-9.-]+ +[0-9.-]+ +(?P<occupancy>[0-9.]+)')
#
# self['Band List'] = []
# for line in theText:
# #volume
# result_volumeSize = re_volumeSize.search(line)
# if result_volumeSize:
# self['Cell Volume'] = float(result_volumeSize.group('cellVolume'))

# #band listings
# result_bandListing = re_bandListing.search(line)
# if result_bandListing:
# theDict = {
# 'band range' : int(result_bandListing.group('bandNum')),
# 'occupancy' : int(float(result_bandListing.group('occupancy'))),
# }
# self['Band List'].append(theDict)
# MissingTags = checkForTags(self, [
# 'Cell Volume',
# ])
# # if missing any tags, or have nothing within the band list
# if MissingTags:
# raise ParseError("ERROR: Missing data in *.scf file", MissingTags)
# if not self['Band List']:
# raise ParseError('ERROR: Missing band list in *.scf file', ())


# Modified by OR (Sat 09 Nov 2013 06:37:11 PM CST)
# it is restricted to determining the band range and cell volume only
class MainSCFParser(AbstractParser):

def parse(self):
tempText = self.getFileContent()

tagList = [
re.compile(r':BAN[0-9]+'),
re.compile(r':VOL'),
re.compile(r':ITE(?P<num>[0-9]+)'),
]
#strip out all of the iterations, volume and band lines
theText = []
Expand All @@ -228,28 +342,10 @@ def parse(self):
if tag.search(line):
theText.append(line)

#grab the last iteration
theIterationIndex, theIterationNumber = 0,0
for number, line in enumerate(theText):
result_theIterationNum = tagList[2].search(line) #ITE regex
if result_theIterationNum:
theIterationNumber = int(result_theIterationNum.group('num'))
theIterationIndex = number
#i'm assuming the last one it finds is the last iteration

#delete up to the last iteration
theText = theText[theIterationIndex:]

re_volumeSize = re.compile(r':VOL +: +UNIT CELL VOLUME = +(?P<cellVolume>[0-9.]+)')
# determine occupied bands
re_bandListing = re.compile(r':BAN[0-9]+: +(?P<bandNum>[0-9]+) +[0-9.-]+ +[0-9.-]+ +(?P<occupancy>[0-9.]+)')

self['Band List'] = []
for line in theText:
#volume
result_volumeSize = re_volumeSize.search(line)
if result_volumeSize:
self['Cell Volume'] = float(result_volumeSize.group('cellVolume'))

#band listings
result_bandListing = re_bandListing.search(line)
if result_bandListing:
Expand All @@ -258,15 +354,23 @@ def parse(self):
'occupancy' : int(float(result_bandListing.group('occupancy'))),
}
self['Band List'].append(theDict)
MissingTags = checkForTags(self, [
'Cell Volume',
])
# if missing any tags, or have nothing within the band list
if MissingTags:
raise ParseError("ERROR: Missing data in *.scf file", MissingTags)
# if have nothing within the band list
if not self['Band List']:
raise ParseError('ERROR: Missing band list in *.scf file', ())

raise ParseError('ERROR: Missing band list in SCF* file', ())

# determine the volume of unit cell
re_volumeSize = re.compile(r':VOL +: +UNIT CELL VOLUME = +(?P<cellVolume>[0-9.]+)')
self['Cell Volume'] = []
for line in theText:
result_volumeSize = re_volumeSize.search(line)
if result_volumeSize:
self['Cell Volume'] = float(result_volumeSize.group('cellVolume'))
# Last value :VOL in *scf will be stored and used in
# calculations. No check for empty volume here,
# since *.scf2 file does not contain volume info

# END MainSCFParser (Sat 09 Nov 2013 06:36:44 PM CST)


class MainOutputstParser(AbstractParser):
def parse(self):
Expand Down
7 changes: 2 additions & 5 deletions readme.org
Original file line number Diff line number Diff line change
@@ -1,10 +1,8 @@
* Current Version
BerryPI 1.0
BerryPI 1.1
* [[https://github.com/spichardo/BerryPI/blob/master/licencing.txt][Licensing Conditions]]
* [[https://github.com/spichardo/BerryPI/blob/master/Installation][Installation Guide]]
* Downloads
** [[https://github.com/spichardo/BerryPI/archive/v1.0.zip][Version 1.0 (Stable)]]
** [[https://github.com/spichardo/BerryPI/archive/master.tar.gz][Latest Snapshot]]
* [[https://github.com/spichardo/BerryPI/archive/master.tar.gz][Download the whole package here]]
* Citation
S.J. Ahmed, J. Kivinen, B. Zaporzan, L. Curiel, S. Pichardo, O. Rubel, Comp. Phys. Commun. 184, 647(2013) ([[http://www.sciencedirect.com/science/article/pii/S0010465512003712?v=s5][Full Text]])

Expand All @@ -17,4 +15,3 @@ The present version is restricted to cases when the lattice vectors correspond t

* To Do
- Non-orthogonal lattice vectors: Extending the capability of "BerryPI" to computing of polarization for structures with non-orthogonal lattice vectors
- Band by band decomposition: Provide analysis of contribution from individual electronic bands (or their range) to the electronic polarization. The present version enables calculation of the Berry phase for a given band range (-b switch), but more testing need to be performed.
Loading

0 comments on commit 34b5f3d

Please sign in to comment.