예제 #1
0
def getEpsilonDist(group='gal', nBins=50, epsCut=2., center='pot'):
    """Returns a histogram of dimension 2 x nbins of stellar epsilons (jz/jcirc) and mass-fraction.  epsCut defines the histogram bound in both directions. Center can be either 'pot' or 'com'"""
    numRotBins   = 400 #number of points at which we linearly interpolate 
    radiusVCM    = 0.25 #fraction of group radius to use when calculating COM velocity
    radiusAngMom = 0.25 #fraction of group radius to use when calculating stellar angular momentum
    
    
    a = charm.getTime()
    if ((group in charm.getGroups()==False)) & (group !='gal'):
        print "Group does not exist, please try again."
        return
    if (group == 'gal'): 
        rgal = quesoConfig.rgalFraction*virialgroup.getVirialGroup()
        center=findcenter.findCenter(group2='virialGroup', method=center)
        charm.createGroupAttributeSphere('gal', 'All', 'position', center[0], center[1], center[2], rgal)
    else:
        center=findcenter.findCenter(group2=group, method=center)
        
    # Find maximum radius
    charm.createGroup_Family('tmp',group,'star')
    maxRad = getgroupradius.getGroupRadius('tmp', center)
    massDist = [0]*(numRotBins+1)
    rad = [0]*(numRotBins+1)
    radialStep = maxRad/numRotBins
    #populate mass bins
    for i in range(numRotBins+1): 
        charm.createGroupAttributeSphere('tmp', 'All', 'position', center[0], center[1], center[2], radialStep*i)
        massDist[i]  = charm.getAttributeSum('tmp','star','mass')
        massDist[i] += charm.getAttributeSum('tmp','dark','mass')
        massDist[i] += charm.getAttributeSum('tmp','gas' ,'mass')
        #Note: I tried shells instead of spheres and it made no real difference.
        rad[i] = radialStep*i
        
    vCM = getVelCMStars(center2=center, radius=radiusVCM*maxRad) #COM velocity
    angMomVec = getNormalStarAngMom(center2=center, radius=radiusAngMom*maxRad, comVel=vCM) #Ang Mom Velocity
    #vCM = getVelCMStars(center2=center, radius=10/(a*quesoConfig.kpcunit)) #COM velocity
    #angMomVec = getNormalStarAngMom(center2=center, radius=6/(a*quesoConfig.kpcunit), comVel=vCM) #Ang Mom Velocity
    
    param = (center, vCM, angMomVec, maxRad, numRotBins,massDist, nBins,epsCut)
    charm.createGroupAttributeSphere('tmp', 'All', 'position', center[0], center[1], center[2], maxRad)
    charm.createGroup_Family('tmp',group,'star')
    #calc total stellar mass for mass weighted average
    reduceResult = charm.reduceParticle('tmp', mapEpsilon, reduceEpsilon, param) 
    sMass = charm.getAttributeSum('tmp','star', 'mass')
    epsilonDist = [0]*nBins
    eps  = [0]*nBins
    for i in range(nBins): eps[i] = -epsCut+ 2*epsCut/nBins*(i)
    for i in range(len(reduceResult)):
        try:
            bin = reduceResult[i][0]
            epsilonDist[bin] = reduceResult[i][1]/sMass #return the mass fraction
        except:{}
    return (eps, epsilonDist)
예제 #2
0
def calcGalacticCoordinates(angMomGroup=None, center ='pot'):
    '''Assigns particles a position in the galactic coordinate system. galVelocity = (v+Hr).  angMomGroup'''
    #===========================================================================
    # --Overview--
    # 1.Form transformation matrix
    # 2.Translate the coordinates to the center of the galaxy (or COM velocity)
    # 3.Rotate the coordinate system to be aligned with the angular momentum vector
    # 4.Write information to vector attributes
    #===========================================================================
    if ((angMomGroup in charm.getGroups())==False) & (angMomGroup!=None):
        print "Group does not exist, please try again."
        return
    ##############################
    # Actual Routine
    ##############################
    if (angMomGroup==None):
        angMomGroup = 'angMomGroup'
        cnt = findcenter.findCenter(method=center)
        virialRadius = virialgroup.getVirialGroup()
        charm.createGroupAttributeSphere('angMomGroup', 'All', 'position', cnt[0], cnt[1], cnt[2], virialRadius*quesoConfig.rgalFraction)
        charm.createGroup_Family('angMomGroup', 'angMomGroup', 'gas')
        charm.createGroup_AttributeRange('angMomGroup', 'angMomGroup', 'temperature', 0, quesoConfig.coldGasTemp)
    else: 
        cnt = findcenter.findCenter(group2=angMomGroup,method=center)
        
    angmom.getAngMomVector(group=angMomGroup,center=center)
    # Transformation Matrix
    galZ = vectormath.normalizeVector(angmom.getAngMomVector(group=angMomGroup,center=center))
    galX = vectormath.normalizeVector(vectormath.crossVectors((0,1,0),galZ))
    galY = vectormath.normalizeVector(vectormath.crossVectors(galZ,galX))
    transMatrix = (galX,
                   galY,
                   galZ)
    
    fHubble       = quesoConfig.fHubble0*math.sqrt(quesoConfig.omega0/charm.getTime()**3+(1-quesoConfig.omega0))
    # Galactic Position                    
    charm.createVectorAttribute('star','galPosition')
    charm.createVectorAttribute('gas', 'galPosition')
    charm.createVectorAttribute('dark','galPosition')
    param = (cnt, transMatrix)
    charm.runLocalParticleCodeGroup('All', calcGalPosition, param)
    # Galactic velocity
    vCM=angmom.getVelCM(angMomGroup)
    param = (cnt, transMatrix,vCM, fHubble)
    charm.createVectorAttribute('star','galVelocity')
    charm.createVectorAttribute('gas', 'galVelocity')
    charm.createVectorAttribute('dark','galVelocity')
    charm.runLocalParticleCodeGroup('All', calcGalVelocity, param)
    return
예제 #3
0
def getHalfMassRadius(group, center='pot') :
    """Returns the current stellar half mass radius."""
    #get the current galactic stellar mass
    rgal = 0.1*virialgroup.getVirialGroup()
    center = findcenter.findCenter(group2=group,method=center)
    halfMass = getFamilyAttributeSum(center,rgal,'star','mass')/2.0
    if (halfMass == 0 ): 
        print "Halfmass is zero inside rgal.  Are there stars inside rgal yet?." 
        return (0,0)
    #Bisection Method to locate half mass
    epsilon = .01
    count = 0
    maxIterations = 50
    a = charm.getTime()
    leftr = .1/(a*quesoConfig.kpcunit)
    rightr = 50/(a*quesoConfig.kpcunit)
    midpoint = (leftr + rightr)/2.0
    leftMass  = getFamilyAttributeSum(center,leftr   ,'star','mass')-halfMass  #Initialize values
    rightMass = getFamilyAttributeSum(center,rightr  ,'star','mass')-halfMass #offset to find root  
    midMass   = getFamilyAttributeSum(center,midpoint,'star','mass')-halfMass #offset so we can find root
    #Bisection to find halfmass radius using initialMass and mass
    #Run until values converge within epsilon or reach max count
    while (count<maxIterations) and (math.fabs((leftMass-rightMass)/halfMass) > epsilon*2.0):
        midpoint = (leftr + rightr)/2.0
        
        #if (math.fabs(leftMass-rightMass)/halfMass < 4*epsilon):break
        leftMass = getFamilyAttributeSum(center,leftr   ,'star','mass')-halfMass  #Initialize values
        rightMass= getFamilyAttributeSum(center,rightr  ,'star','mass')-halfMass #offset to find root  
        midMass  = getFamilyAttributeSum(center,midpoint,'star','mass')-halfMass #offset so we can find root
        #print str((leftMass,midMass,rightMass)) + "    " + str(math.fabs(leftMass-rightMass)/halfMass) +str((leftr,midpoint,rightr))
        if (leftMass*midMass<0)   : rightr = midpoint
        elif (rightMass*midMass<0): leftr  = midpoint
        elif (midMass==0)         : break
        elif (leftMass*midMass>0) and (rightMass*midMass>0):
            print "\nStellar half mass radius will not converge. Try larger bounds."
            return
        count += 1
    #Don't get stuck in a loop
    if (count==maxIterations): 
        print "\nDid not converge in " + str(maxIterations) + " iterations.  Try smaller bounds or raise epsilon in source."
        return
    resultVec=midpoint #already in units of kpc taking into account the expansion factor
    #print resultVec[i]
    return resultVec