The electron configuration of an atom is the specification of the distribution of its electrons in atomic orbitals. An atomic orbital is identified by a principal quantum number, $n = 1,2,3,\cdots$ defining a shell comprised of one or more subshells defined by the azimuthal quantum number, $l=0,1,2,\cdots{n-1}$. The values $l=0,1,2,3$ are refered to be the letters $s$, $p$, $d$, and $f$ respectively. Thus, the first few orbitals are: 1s ($n=1, l=0$), 2s ($n=2, l=0$), 2p ($n=2, l=1$), 3s ($n=3, l=0$), and each shell has $n$ subshells. A maximum of $2(2l+1)$ electrons may occupy a given subshell.
According to the Madelung rule, the $N$ electrons of an atom fill the orbitals in order of increasing $n+l$ such that whenever two orbitals have the same value of $n+l$, they are filled in order of increasing $n$. For example, the ground state of Titanium ($N=22$) is predicted (and found) to be $1s^22s^22p^63s^23p^64s^23d^2$.
Write a program to predict the electronic configurations of the elements up to Rutherfordium ($N=104$). The output for Titanium should be
Ti: 1s2.2s2.2p6.3s2.3p6.4s2.3d2
A Python list containing the element symbols is here: element_symbols.py
As a bonus exercise, modify your program to output the configurations using the convention that the part of the configuration corresponding to the outermost closed shell, a noble gas configuration, is replaced by the noble gas symbol in square brackets, thus:
Ti: [Ar].4s2.3d2
the configuration of Argon being 1s2.2s2.2p6.3s2.3p6
.
This program deduces the number of electrons in each atom from its position in the list, element_symbols.py
.
# All element symbols up to Rf
from element_symbols import element_symbols
# Letters identifying subshells
l_letter = ['s', 'p', 'd', 'f', 'g']
def get_config_str(config):
""" Turn a list of orbital, nelec pairs into a configuration string. """
return '.'.join(['{:2s}{:d}'.format(*e) for e in config])
# Create and order a list of tuples, (n+l, n, l), corresponding to the order
# in which the corresponding orbitals are filled using the Madelung rule.
nl_pairs = []
for n in range(1,8):
for l in range(n):
nl_pairs.append((n+l, n, l))
nl_pairs.sort()
# inl indexes the subshell in the nl_pairs list; nelec is the number of
# electrons currently inhabiting this subshell
inl, nelec = 0, 0
# start with the 1s orbital
n, l = 1, 0
# a list of orbitals and the electrons they contain for a configuration
config = [['1s', 0]]
for element in element_symbols:
nelec += 1
if nelec > 2*(2*l+1):
# this subshell is now full: start a new subshell
inl += 1
_, n, l = nl_pairs[inl]
config.append(['{}{}'.format(n, l_letter[l]), 1])
nelec = 1
else:
# add an electron to the current subshell
config[-1][1] += 1
# Turn config into a string and output it
s_config = get_config_str(config)
print('{:2s}: {}'.format(element, s_config))
Output:
H : 1s1
He: 1s2
Li: 1s2.2s1
Be: 1s2.2s2
B : 1s2.2s2.2p1
C : 1s2.2s2.2p2
N : 1s2.2s2.2p3
...
The following version of the program does some additional work to output the closed-shell part of the configuration as a noble gas element symbol:
# All element symbols up to Rf
from element_symbols import element_symbols
# Letters identifying subshells
l_letter = ['s', 'p', 'd', 'f', 'g']
def get_config_str(config):
""" Turn a list of orbital, nelec pairs into a configuration string. """
return '.'.join(['{:2s}{:d}'.format(*e) for e in config])
# Create and order a list of tuples, (n+l, n, l), corresponding to the order
# in which the corresponding orbitals are filled using the Madelung rule.
nl_pairs = []
for n in range(1,8):
for l in range(n):
nl_pairs.append((n+l, n, l))
nl_pairs.sort()
# inl indexes the subshell in the nl_pairs list; nelec is the number of
# electrons currently inhabiting this subshell
inl, nelec = 0, 0
# start with the 1s orbital
n, l = 1, 0
# a list of orbitals and the electrons they contain for a configuration
config = [['1s', 0]]
# Store the most recent Noble gas configuration encountered in a tuple with the
# corresponding element symbol
noble_gas_config = ('', '')
for i, element in enumerate(element_symbols):
nelec += 1
if nelec > 2*(2*l+1):
# this subshell is now full
if l == 1:
# The most recent configuration was for a Noble gas: store it
noble_gas_config = (get_config_str(config),
'[{}]'.format(element_symbols[i-1]))
# Start a new subshell
inl += 1
_, n, l = nl_pairs[inl]
config.append(['{}{}'.format(n, l_letter[l]), 1])
nelec = 1
else:
# add an electron to the current subshell
config[-1][1] += 1
# Turn config into a string
s_config = get_config_str(config)
# Replace the heaviest Noble gas configuration with its symbol
s_config = s_config.replace(*noble_gas_config)
print('{:2s}: {}'.format(element, s_config))
Hence:
...
Md: [Rn].7s2.5f13
No: [Rn].7s2.5f14
Lr: [Rn].7s2.5f14.6d1
Rf: [Rn].7s2.5f14.6d2