Ejemplo n.º 1
0
    def gen_struct_from_hilbert_curve(self, newd):
        '''
        Generates new structures at the points along the
        Hilbert curve given in newd, and returns their
        scaled coordinates.
        '''

        dpar = np.array(self.dparams)
        parmin = np.array(self.params) - dpar
        ranges = []
        [
            ranges.append([self.params[i] - dpar[i], self.params[i] + dpar[i]])
            for i in range(len(self.params))
        ]
        coordinates = []
        for i in range(0, len(newd)):

            # interpolate to get the coordingates:
            p_ipl = self.hutil.interp_coords_from_dist(newd[i])

            # un-scale it and create structure
            parnew = np.array(p_ipl)

            #par_unscaled = parnew*2*dpar/self.hutil.pmax + parmin
            par_unscaled = np.squeeze(
                self.hutil.scale_coordinates(parnew, dpar, parmin))

            # generate strucure:
            news = Structure(self.orig)
            pindex = 0

            # Layer widths:
            for i in range(0, len(self.windex)):
                news.layers[self.windex[i]].width = par_unscaled[pindex]
                pindex += 1

            news.dopings = []

            dop_start = 0
            dop_step = int(len(self.dopindex) / len(self.orig.dopings))
            for d in self.orig.dopings:

                # Doping layers:
                z0 = d[0]
                zend = d[1]
                doping = d[2]
                center = (z0 + zend) / 2
                width = (zend - z0)
                sheet = width * doping
                zizfdens = [center, width, doping]

                dop_end = dop_start + dop_step

                for i in range(dop_start, dop_end):

                    zizfdens[self.dopindex[i]] = par_unscaled[pindex]

                    pindex += 1

                dop_start = dop_end

                if (self.doping_mode == doping_modes.get("FOLLOW LAYER SHEET")
                        or self.doping_mode
                        == doping_modes.get("FOLLOW LAYER VOLUME")):

                    layerindex = self.orig.layerIndex(center)
                    z0 = news.layerPos(layerindex)
                    zend = z0 + news.layers[layerindex].width

                    if (self.doping_mode == doping_modes.get(
                            "FOLLOW LAYER SHEET")):
                        doping = zizfdens[2] * width / (zend - z0)
                    else:
                        doping = zizfdens[2]

                else:
                    z0 = zizfdens[0]
                    zend = zizfdens[1]

                    if (self.doping_mode == doping_modes.get(
                            "FIXED POSITION SHEET")):
                        doping = zizfdens[2] / width * (zend - z0)
                    else:
                        doping = zizfdens[2]

                    doping = zizfdens[2]

                news.addDoping(z0, zend, doping)

            # Alloy composition:
            tags = []
            ptag = []
            for i in range(0, len(self.xindex)):

                if self.comp_mode == comp_modes.get("UNLINKED"):
                    news.layers[self.xindex[i]].material.updateAlloy(
                        par_unscaled[pindex])
                    pindex += 1
                elif self.comp_mode == comp_modes.get("LINKED ALL"):
                    news.layers[self.xindex[i]].material.updateAlloy(
                        par_unscaled[pindex])
                    pass
                elif self.comp_mode == comp_modes.get("LINKED LAYERS"):
                    print("Layers are linked:")
                    tag = self.tagindex[i]
                    print("tag = ", tag)
                    if tag not in tags:
                        tags.append(tag)
                        ptag.append(pindex)
                    else:
                        pindex = ptag[tags.index(tag)]

                    print("pindex = ", pindex)
                    news.layers[self.xindex[i]].material.updateAlloy(
                        par_unscaled[pindex])
                    news.layers[self.xindex[i]].material.name += str(tag)

                    if len(ptag) > 0:
                        pindex = np.max(ptag) + 1
                    else:
                        pindex += 1

            if self.width_mode == width_modes.get("MONOLAYER"):
                news.convert_to_ML()
            if self.strain_mode == strain_modes.get("COMPENSATE X"):
                news.compensate_strain()

            self.structures.append(news)

            coordinates.append(parnew)

        return coordinates
Ejemplo n.º 2
0
    def generateStructure(self, params):
        # generate strucure:
        news = Structure(self.orig)
        pindex = 0

        # Layer widths:
        for i in range(0,len(self.windex)):
            news.layers[self.windex[i]].width = params[pindex]
            pindex+=1

        news.dopings = []

        dop_start = 0
        dop_step = int(len(self.dopindex)/len(self.orig.dopings))
        for d in self.orig.dopings:

            # Doping layers:
            z0 = d[0]
            zend = d[1]
            doping = d[2]
            center = (z0 + zend)/2
            width = (zend - z0)
            sheet = width*doping
            zizfdens = [center, width, doping]

            dop_end = dop_start + dop_step

            for i in range(dop_start,dop_end):

                zizfdens[self.dopindex[i]] = params[pindex]

                pindex +=1

            dop_start = dop_end

            if (self.doping_mode == doping_modes.get("FOLLOW LAYER SHEET") or
                self.doping_mode == doping_modes.get("FOLLOW LAYER VOLUME")):

                layerindex = self.orig.layerIndex(center)
                z0 = news.layerPos(layerindex)
                zend = z0 + news.layers[layerindex].width

                if (self.doping_mode == doping_modes.get("FOLLOW LAYER SHEET") ):
                    doping = zizfdens[2]*width/(zend-z0)
                else:
                    doping = zizfdens[2]

            else:
                z0 = zizfdens[0]
                zend = zizfdens[1]

                if (self.doping_mode == doping_modes.get("FIXED POSITION SHEET") ):
                    doping = zizfdens[2]/width*(zend-z0)
                else:
                    doping = zizfdens[2]

                doping = zizfdens[2]

            news.addDoping(z0,zend,doping)

        # Alloy composition:
        tags = []
        ptag = []
        for i in range(0,len(self.xindex)):


            if self.comp_mode == comp_modes.get("UNLINKED"):
                news.layers[self.xindex[i]].material.updateAlloy(params[pindex])
                pindex +=1
            elif self.comp_mode == comp_modes.get("LINKED ALL"):
                news.layers[self.xindex[i]].material.updateAlloy(params[pindex])
                pass
            elif self.comp_mode == comp_modes.get("LINKED LAYERS"):
                print("Layers are linked:")
                tag = self.tagindex[i]
                print("tag = ", tag)
                if tag not in tags:
                    tags.append(tag)
                    ptag.append(pindex)
                else:
                    pindex = ptag[tags.index(tag)]

                print("pindex = ", pindex)
                news.layers[self.xindex[i]].material.updateAlloy(params[pindex])
                news.layers[self.xindex[i]].material.name += str(tag)


                if len(ptag) > 0:
                    pindex = np.max(ptag) + 1
                else:
                    pindex += 1

        if self.width_mode == width_modes.get("MONOLAYER"):
            news.convert_to_ML()
        if self.strain_mode == strain_modes.get("COMPENSATE X"):
            news.compensate_strain()

        return news
Ejemplo n.º 3
0
    def genRanStructs(self, N):
        """
        Generate N structures with random variations in layer widths.
        Doping modes "FOLLOW LAYER SHEET/VOLUME" assume that doping
        covers entire layer width.
        Doping modes "FIXED WIDTH SHEET/VOLUME" changes doping pos.
        independently of layer widths.
        TODO: Change compositions!
        """
        for _ in range(0, N):
            news = Structure(self.orig)

            for il in range(len(self.dw)):
                w0 = self.orig.layers[il].width
                width = w0 + 2 * (random.random() - 0.5) * self.dw[il]
                news.layers[il].width = width

            news.dopings = []
            for dl in self.orig.dopings:

                zc = (dl[0] + dl[1]) / 2
                layerindex = self.orig.layerIndex(zc)
                sheet = self.orig.layers[layerindex].width * dl[2]

                if (self.doping_mode == doping_modes.get("FOLLOW LAYER SHEET")
                        or self.doping_mode
                        == doping_modes.get("FOLLOW LAYER VOLUME")):

                    zi = 0
                    zf = news.layers[layerindex].width

                    if self.doping_mode == doping_modes.get(
                            "FOLLOW LAYER SHEET"):
                        dopdens = sheet / news.layers[layerindex].width
                    else:
                        dopdens = dl[2]

                    dopdens = dopdens + 2 * (random.random() -
                                             0.5) * self.ddop[2]

                else:

                    dzc = zc - self.orig.layerPos(layerindex)

                    # define new offset from layer start
                    dzc = dzc + 2 * (random.random() - 0.5) * self.ddop[0]
                    dopw = (dl[1] -
                            dl[0]) + 2 * (random.random() - 0.5) * self.ddop[1]

                    # add new doping layer
                    zi = dzc - dopw / 2
                    zf = dzc + dopw / 2

                    if self.doping_mode == doping_modes.get(
                            "FIXED POSITION SHEET"):
                        dopdens = sheet / (zf - zi)
                    else:
                        dopdens = dl[2]

                    dopdens = dopdens + 2 * (random.random() -
                                             0.5) * self.ddop[2]

                news.addDoping(zi, zf, dopdens, layerindex)

            if self.strain_mode == strain_modes.get("COMPENSATE X"):
                news.compensate_strain()

            self.structures.append(news)
            del news