Pregunta

I necesidad de elaborar parcelas / triángulo ternarias representa fracciones molares ( x , y , z ) de varias sustancias / mezclas ( x + y + z = 1). Cada parcela representa sustancias iso-valor, por ejemplo, sustancias que tienen el mismo punto de fusión. Las parcelas tienen que ser dibujado en el mismo triángulo con diferentes colores / símbolos y sería bueno si yo también podría conectar los puntos.

He mirado matplotlib, R y gnuplot, pero que no parecen ser capaces de elaborar este tipo de trama. La tercera parte ade4 paquete para R parece ser capaz de dibujar, pero no estoy seguro de si puedo dibujar varias parcelas en el mismo triángulo.

Necesito algo que funciona bajo Linux o Windows. Estoy abierto a cualquier sugerencia, incluidas las bibliotecas de otros idiomas, por ejemplo, Perl, PHP, Ruby, C # y Java.

¿Fue útil?

Solución

R tiene un paquete externo llamado VCD que debe hacer lo que quiera.

La documentación es muy buena (122 manual de página distribuye w / el paquete); también hay un libro del mismo nombre, Visual Display de información cuantitativa , por el autor del paquete (Prof. Michael friendly).

Para crear diagrama ternario utilizando VCD , simplemente llame ternaryplot () y pasar en una matriz de mx 3, es decir, una matriz con tres columnas.

La firma del método es muy simple; sólo se requiere un único parámetro (la matriz m x datos 3); y todos los parámetros de palabras clave se relacionan con la estética de la trama, a excepción de la escala, que cuando se establece en 1, normaliza los datos de columna se refiere.

Para representar puntos de datos en el diagrama ternario, las coordenadas de un punto dado se calculan como la centro de gravedad de puntos de masa en el que cada valor de la característica comprende la matriz de datos es una separada peso , por lo tanto, las coordenadas de un punto V (a, b, c) son

V(b, c/2, c * (3^.5)/2

Para generar el siguiente diagrama, que acaba de crear algunos datos falsos para representar cuatro mezclas químicas diferentes, cada uno compuesto de diferentes fracciones de tres sustancias (x, y, z). Escalé la entrada (lo que x + y + z = 1) pero la función haré por ti si se pasa en un valor para el parámetro 'escala' (de hecho, el valor predeterminado es 1, que creo que es lo que su pregunta requiere). He utilizado diferentes colores y símbolos para representar los cuatro puntos de datos, pero también se puede utilizar sólo un color / símbolo único y etiquetar cada punto (a través de la discusión 'id').

Otros consejos

Creado un guión muy básico para la generación diagrama ternario (o más). No hay líneas de división o ticklines, pero los que no sería demasiado difícil añadir usando los vectores de la matriz "base".

introducir descripción de la imagen aquí

from pylab import *


def ternaryPlot(
            data,

            # Scale data for ternary plot (i.e. a + b + c = 1)
            scaling=True,

            # Direction of first vertex.
            start_angle=90,

            # Orient labels perpendicular to vertices.
            rotate_labels=True,

            # Labels for vertices.
            labels=('one','two','three'),

            # Can accomodate more than 3 dimensions if desired.
            sides=3,

            # Offset for label from vertex (percent of distance from origin).
            label_offset=0.10,

            # Any matplotlib keyword args for plots.
            edge_args={'color':'black','linewidth':2},

            # Any matplotlib keyword args for figures.
            fig_args = {'figsize':(8,8),'facecolor':'white','edgecolor':'white'},
        ):
    '''
    This will create a basic "ternary" plot (or quaternary, etc.)
    '''
    basis = array(
                    [
                        [
                            cos(2*_*pi/sides + start_angle*pi/180),
                            sin(2*_*pi/sides + start_angle*pi/180)
                        ] 
                        for _ in range(sides)
                    ]
                )

    # If data is Nxsides, newdata is Nx2.
    if scaling:
        # Scales data for you.
        newdata = dot((data.T / data.sum(-1)).T,basis)
    else:
        # Assumes data already sums to 1.
        newdata = dot(data,basis)

    fig = figure(**fig_args)
    ax = fig.add_subplot(111)

    for i,l in enumerate(labels):
        if i >= sides:
            break
        x = basis[i,0]
        y = basis[i,1]
        if rotate_labels:
            angle = 180*arctan(y/x)/pi + 90
            if angle > 90 and angle <= 270:
                angle = mod(angle + 180,360)
        else:
            angle = 0
        ax.text(
                x*(1 + label_offset),
                y*(1 + label_offset),
                l,
                horizontalalignment='center',
                verticalalignment='center',
                rotation=angle
            )

    # Clear normal matplotlib axes graphics.
    ax.set_xticks(())
    ax.set_yticks(())
    ax.set_frame_on(False)

    # Plot border
    ax.plot(
        [basis[_,0] for _ in range(sides) + [0,]],
        [basis[_,1] for _ in range(sides) + [0,]],
        **edge_args
    )

    return newdata,ax


if __name__ == '__main__':
    k = 0.5
    s = 1000

    data = vstack((
        array([k,0,0]) + rand(s,3), 
        array([0,k,0]) + rand(s,3), 
        array([0,0,k]) + rand(s,3)
    ))
    color = array([[1,0,0]]*s + [[0,1,0]]*s + [[0,0,1]]*s)

    newdata,ax = ternaryPlot(data)

    ax.scatter(
        newdata[:,0],
        newdata[:,1],
        s=2,
        alpha=0.5,
        color=color
        )
    show()

Un paquete que he escrito en R tiene solo sido aceptado para CRAN, página web es www.ggtern .com :

Se basa fuera ggplot2 , que he utilizado como plataforma. La fuerza motriz para mí, era un deseo de tener consistencia en mi trabajo, y, desde que uso ggplot2 en gran medida, el desarrollo del paquete era una progresión lógica.

Para aquellos de ustedes que usan ggplot2, el uso de ggtern debe ser una brisa, y, aquí está un par de demostraciones de lo que puede lograrse.

feldespato

Producido por el código siguiente:

# Load data
data(Feldspar)

# Sort it by decreasing pressure 
# (so small grobs sit on top of large grobs
Feldspar <- Feldspar[with(Feldspar, order(-P.Gpa)), ]

# Build and Render the Plot
ggtern(data = Feldspar, aes(x = An, y = Ab, z = Or)) + 
#the layer
geom_point(aes(fill = T.C, 
               size = P.Gpa, 
               shape = Feldspar)) + 
#scales
scale_shape_manual(values = c(21, 24)) + 
scale_size_continuous(range = c(2.5, 7.5)) + 
scale_fill_gradient(low = "green", high = "red") + 

#theme tweaks
theme_tern_bw()  + 
theme(legend.position      = c(0, 1), 
      legend.justification = c(0, 1), 
      legend.box.just      = "left") + 

#tweak guides
guides(shape= guide_legend(order   =1,
                           override.aes=list(size=5)),
       size = guide_legend(order   =2),
       fill = guide_colourbar(order=3)) +

#labels and title
labs(size = "Pressure/GPa", 
     fill = "Temperature/C") + 
ggtitle("Feldspar - Elkins and Grove 1990")

Diagramas de contorno también han sido parcheado para el medio ambiente ternario, y, una inclusión de una nueva geometría para representar los intervalos de confianza a través de la Mahalanobis Distancia .

Contour

Producido por el código siguiente:

ggtern(data=Feldspar,aes(An,Ab,Or)) +
  geom_confidence(aes(group=Feldspar,
                      fill=..level..,
                      alpha=1-..level..),
                      n=2000,
                  breaks=c(0.01,0.02,0.03,0.04,
                           seq(0.05,0.95,by=0.1),
                           0.99,0.995,0.9995),
                  color=NA,linetype=1) +
  geom_density2d(aes(color=..level..)) + 
  geom_point(fill="white",aes(shape=Feldspar),size=5) +  
  theme_tern_bw() + 
  theme_tern_nogrid() + 
  theme(ternary.options=element_ternary(padding=0.2),
                        legend.position=c(0,1),
                        legend.justification=c(0,1),
                        legend.box.just="left") +
  labs(color="Density",fill="Confidence",
   title="Feldspar - Elkins and Grove 1990 + Confidence Levels + Density") +
  scale_color_gradient(low="gray",high="magenta") +
  scale_fill_gradient2(low="red",mid="orange",high="green",
                       midpoint=0.8) +
  scale_shape_manual(values=c(21,24)) + 
  guides(shape= guide_legend(order   =1,
                             override.aes=list(size=5)),
         size = guide_legend(order   =2),
         fill = guide_colourbar(order=3),
         color= guide_colourbar(order=4),
         alpha= "none")

Veusz apoya diagrama ternario. Aquí está un ejemplo de la : Ejemplo trama

Chloë Lewis desarrolló una clase general de triángulo trama, destinado a apoyar el triángulo de la textura del suelo con Python y Matplotlib. Está disponible aquí http://nature.berkeley.edu/~chlewis/Sourcecode.html https : //github.com/chlewissoil/TernaryPlotPy

edición de Chloe para añadir: Movido a una serie más fiable! Además, es un acuerdo de recompra pública, por lo que si desea solicitar biblioteca-ización, se podría añadir un problema. Esperamos que sea útil a alguien.

acabo de descubrir una herramienta que utiliza Python / Matplotlib para generar diagrama ternario llamados wxTernary. Está disponible a través de http://wxternary.sourceforge.net/ - yo era capaz de generar con éxito un diagrama ternario en el primer intento.

Parece que hay una aplicación en el trabajo aquí en gnuplot: diagrama ternario
(fuente: ugm.ac.id )

Encuentra una biblioteca de dibujo vectorial y dibujar desde cero si no se puede encontrar una manera más fácil de hacerlo.

Hay un paquete de R llamado soiltexture . Está dirigido a trama triángulo de la textura del suelo, pero se puede personalizar para algunos aspectos.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top