Ejemplo n.º 1
0
        private void GenerateSymmetries()
        {
            Symmetries = new SymmetryList();
            Symmetries.Add(new Symmetry(Matrix.Identity(3)));

            foreach (var sym in PrimitiveSymmetries)
            {
                Symmetries.Add(sym.Clone());

                GenerateSymmetries(sym);
            }
        }
Ejemplo n.º 2
0
        private static SymmetryList FindCompatibleSymmetries(int[] kgrid, SymmetryList syms)
        {
            SymmetryList compatSyms;

            compatSyms = new SymmetryList();
            Vector3 gridVector = new Vector3(kgrid[0], kgrid[1], kgrid[2]);

            foreach (var symmetry in syms)
            {
                Vector3 grid2 = symmetry.Value * gridVector;
                for (int gi = 0; gi < 3; gi++)
                {
                    grid2[gi] = Math.Abs(grid2[gi]);
                }

                if (grid2 == gridVector)
                {
                    compatSyms.Add(symmetry);
                }
            }
            return(compatSyms);
        }
Ejemplo n.º 3
0
        public static KptList oldGenerateMesh(Lattice lattice, int[] kgrid, int[] shift, SymmetryList syms, bool includeEnds)
        {
            bool    centerGamma = false;
            KptList retval      = new KptList();
            int     zmax        = kgrid[2] * 2;
            int     ymax        = kgrid[1] * 2;
            int     xmax        = kgrid[0] * 2;

            if (shift == null)
            {
                shift = new int[3];
            }

            retval.mesh          = (int[])kgrid.Clone();
            retval.shift         = (int[])shift.Clone();
            retval.gammaCentered = centerGamma;

            int     index      = 0;
            Vector3 gridVector = new Vector3(kgrid[0], kgrid[1], kgrid[2]);

            SymmetryList compatSyms = new SymmetryList();

            foreach (var symmetry in syms)
            {
                Vector3 grid2 = symmetry.Value * gridVector;
                for (int gi = 0; gi < 3; gi++)
                {
                    grid2[gi] = Math.Abs(grid2[gi]);
                }

                if (grid2 == gridVector)
                {
                    compatSyms.Add(symmetry);
                }
            }

            for (int k = 0; k <= zmax; k += 2)
            {
                for (int j = 0; j <= ymax; j += 2)
                {
                    for (int i = 0; i <= xmax; i += 2)
                    {
                        if (includeEnds == false)
                        {
                            if (k == zmax)
                            {
                                break;
                            }
                            if (i == xmax)
                            {
                                break;
                            }
                            if (j == ymax)
                            {
                                break;
                            }
                        }

                        int  N        = retval.KptToInteger(i, j, k);
                        bool foundSym = false;

                        double     dx       = (i + shift[0]) / (double)xmax;
                        double     dy       = (j + shift[1]) / (double)ymax;
                        double     dz       = (k + shift[2]) / (double)zmax;
                        int        symN     = N;
                        List <int> orbitals = null;

                        if (centerGamma)
                        {
                            if (kgrid[0] > 1)
                            {
                                dx -= 0.5;
                            }
                            if (kgrid[1] > 1)
                            {
                                dy -= 0.5;
                            }
                            if (kgrid[2] > 1)
                            {
                                dz -= 0.5;
                            }
                        }

                        Vector3 pt = CalcK(lattice, dx, dy, dz);

#if DEBUG
                        int testi, testj, testk;
                        retval.ReduceKpt(lattice, new Vector3(pt), out testi, out testj, out testk);

                        //System.Diagnostics.Debug.Assert(i == testi);
                        //System.Diagnostics.Debug.Assert(j == testj);
                        //System.Diagnostics.Debug.Assert(k == testk);
#endif
                        foreach (var symmetry in compatSyms)
                        {
                            Vector3 Tpt = symmetry.Value * pt;

                            if (Tpt == pt)
                            {
                                continue;
                            }

                            Vector3 red = lattice.ReducedCoords(Tpt, true);

                            int newi = (int)Math.Round(xmax * red.X - shift[0]);
                            int newj = (int)Math.Round(ymax * red.Y - shift[1]);
                            int newk = (int)Math.Round(zmax * red.Z - shift[2]);

                            if (newi % 2 != 0 || newj % 2 != 0 || newk % 2 != 0)
                            {
                                continue;
                            }

                            symN = retval.KptToInteger(newi, newj, newk);

                            if (symN < N)
                            {
                                foundSym = true;

                                if (symmetry.OrbitalTransform.Count > 0)
                                {
                                    orbitals = symmetry.OrbitalTransform;
                                }
                            }

                            if (foundSym)
                            {
                                break;
                            }
                        }

                        Vector3 kptValue = CalcK(lattice, dx, dy, dz);

                        retval.allKpts.Add(new KPoint(kptValue));

                        if (retval.Nvalues.ContainsKey(N))
                        {
                        }
                        else if (foundSym == false)
                        {
                            retval.kpts.Add(new KPoint(kptValue));
                            retval.Nvalues.Add(N, index);
                            index++;
                        }
                        else
                        {
                            int newIndex = retval.Nvalues[symN];
                            retval.kpts[newIndex].Weight++;
                            retval.kpts[newIndex].AddOrbitalSymmetry(orbitals);

                            retval.Nvalues.Add(N, newIndex);
                        }
                    }
                }
            }

            int count = kgrid[0] * kgrid[1] * kgrid[2];
            for (int i = 0; i < retval.kpts.Count; i++)
            {
                retval.kpts[i].Weight    /= count;
                retval.allKpts[i].Weight /= count;
            }

            if (includeEnds)
            {
                retval.allKpts.Sort((x, y) => x.Value.Z.CompareTo(y.Value.Z));

                List <int> removeThese = new List <int>();
                List <int> equivKpt    = new List <int>();

                // read this value first, because the size of the array will change.
                int kptCount = retval.AllKpts.Count;
                for (int kindex = 0; kindex < kptCount; kindex++)
                {
                    if (removeThese.Contains(kindex))
                    {
                        continue;
                    }

                    Vector3 kpt  = retval.allKpts[kindex].Value;
                    double  dist = kpt.Magnitude;

                    equivKpt.Clear();

                    for (int k = -1; k <= 1; k++)
                    {
                        for (int j = -1; j <= 1; j++)
                        {
                            for (int i = -1; i <= 1; i++)
                            {
                                if (i == 0 && j == 0 && k == 0)
                                {
                                    continue;
                                }

                                Vector3 pt = kpt +
                                             i * lattice.G1 +
                                             j * lattice.G2 +
                                             k * lattice.G3;

                                double newDist = pt.Magnitude;

                                if (newDist < dist - 1e-6)
                                {
                                    foreach (var value in equivKpt)
                                    {
                                        if (removeThese.Contains(value) == false)
                                        {
                                            removeThese.Add(value);
                                        }
                                    }

                                    equivKpt.Clear();

                                    int search = retval.AllKpts.FindIndex(x => (x.Value - pt).Magnitude < 1e-6);

                                    if (search != -1)
                                    {
                                        if (removeThese.Contains(kindex) == false)
                                        {
                                            removeThese.Add(kindex);
                                        }

                                        // break out of the loop
                                        k = 1; j = 1; i = 2;
                                    }
                                    else
                                    {
                                        retval.allKpts[kindex].Value = pt;
                                        kpt  = pt;
                                        dist = newDist;

                                        // reset variables since we updated this kpoint value.
                                        k = -1;
                                        j = -1;
                                        i = -2;
                                    }
                                }
                                else if (Math.Abs(dist - newDist) < 1e-6)
                                {
                                    int search = retval.AllKpts.FindIndex(x => (x.Value - pt).Magnitude < 1e-6);

                                    if (search != -1)
                                    {
                                        if (removeThese.Contains(search))
                                        {
                                            k = 1; j = 1; i = 2;
                                            removeThese.Add(kindex);
                                            break;
                                        }

                                        equivKpt.Add(search);
                                        continue;
                                    }

                                    equivKpt.Add(retval.allKpts.Count);
                                    retval.allKpts.Add(new KPoint(pt));
                                }
                            }
                        }
                    }
                }

                // sort in reverse order
                removeThese.Sort((x, y) => - x.CompareTo(y));

                for (int i = 0; i < removeThese.Count; i++)
                {
                    retval.allKpts.RemoveAt(removeThese[i]);
                }

                retval.allKpts.Sort((x, y) => x.Value.Z.CompareTo(y.Value.Z));
            }
#if DEBUG
            if (!includeEnds)
            {
                double check = 0;
                for (int i = 0; i < retval.kpts.Count; i++)
                {
                    check += retval.kpts[i].Weight;
                }

                System.Diagnostics.Debug.Assert(Math.Abs(check - 1) < 1e-8);
            }
#endif

            return(retval);
        }
Ejemplo n.º 4
0
        static void Initialize()
        {
            if (init)
            {
                return;
            }
            init = true;

            InitializeRegex();
            string groups = Properties.Resources.spgroup;

            using (StringReader r = new StringReader(groups))
            {
                for (; ;)
                {
                    string groupName = r.ReadLine().Trim();
                    int    number;

                    if (groupName.EndsWith("&"))
                    {
                        break;
                    }

                    if (int.TryParse(groupName.Substring(1, groupName.Length - 2), out number) == false)
                    {
                        throw new Exception();
                    }


                    SpaceGroup sp = new SpaceGroup();
                    sp.Number = number;

                    for (; ;)
                    {
                        if (r.Peek() == '/')
                        {
                            break;
                        }

                        string text      = r.ReadLine();
                        int    lastColon = text.IndexOf(":", 8);

                        var sym = ParseSymmetry(text);
                        sym.Name = text.Substring(lastColon + 1).Trim();

                        if (sym.Value.IsIdentity)
                        {
                            continue;
                        }

                        if (mPrimitiveSymmetries.Contains(sym) == false)
                        {
                            mPrimitiveSymmetries.Add(sym);
                        }

                        sp.PrimitiveSymmetries.Add(sym);
                    }

                    mGroups.Add(number, sp);
                }
            }

            using (StringReader r = new StringReader(Properties.Resources.spnames))
            {
                for (; ;)
                {
                    string text = r.ReadLine();

                    if (text == "&")
                    {
                        break;
                    }

                    string[] vals = text.Split('-');

                    int    number = int.Parse(vals[0]);
                    string name   = vals[1].Trim();

                    mGroups[number].Name = name;
                }
            }
        }