¿Cómo construir un Screener de Trading Efectivo con Python y TradingView?

0
44
Recomendaciones de compra, venta, neutralidad, acciones

Los screeners de trading son herramientas indispensables para los traders e inversores que buscan oportunidades en los vastos mercados financieros. Al aplicar criterios e indicadores específicos para filtrar entre una multitud de instrumentos, podemos descubrir posibles operaciones con mayores probabilidades de éxito.

Para lograr esto, aprovecharemos la biblioteca tradingview_ta, una poderosa biblioteca de Python que proporciona acceso a una amplia gama de indicadores actualizados y populares utilizados por traders en todo el mundo. Esto nos asegura estar a la vanguardia al incorporar las últimas perspectivas del mercado en nuestro proceso de selección. También utilizaremos la biblioteca yfinance para descargar fácilmente cotizaciones históricas de nuestros instrumentos seleccionados, lo que nos brinda una sólida base de datos histórica para un análisis y pruebas exhaustivos.

Este artículo se centrará en una aplicación práctica utilizando acciones del mercado de Estados Unidos. Sin embargo, es importante destacar que los principios y técnicas que exploraremos se pueden aplicar a una amplia gama de instrumentos disponibles en TradingView. Ya sea que te interesen acciones, futuros, ETFs, criptomonedas o cualquier otro activo negociable, este screener puede adaptarse a tus necesidades.

En la primera parte, creamos un gráfico donde podemos ver visualmente cuántos indicadores técnicos señalan compra o venta para cada una de las acciones analizadas. Luego, en la segunda sección, descargamos el detalle de cada uno de los indicadores técnicos para filtrar y buscar oportunidades de trading en activos específicos.

Más información sobre la plataforma TradingView y sus múltiples herramientas de análisis en: Reseña de TradingView

Paso 1: Importación de bibliotecas

Primero importaremos bibliotecas esenciales como pandas, numpy, tradingview_ta, yfinance, mplfinance, datetime y matplotlib. Estas bibliotecas nos permitirán manejar datos, realizar screeners, visualizar resultados y crear gráficos.

#Importar las librerías que vamos a utilizar para el análisis.
import pandas as pd
import numpy as np
from tradingview_ta import TA_Handler, Interval, Exchange
import yfinance as yf
import mplfinance as mpf
from datetime import datetime, timedelta
import matplotlib.pyplot as plt

Paso 2: Definir la lista de acciones

En el fragmento de código proporcionado, tenemos una lista de símbolos de ticker que representan un conjunto de acciones del mercado de valores estadounidenses. Esta lista incluye valores como Apple, Tesla, Nvidia, Boeing y otros bastante conocidos.

Al incluir estos símbolos de ticker en nuestro código, estamos creando esencialmente una lista de seguimiento o un conjunto de instrumentos que queremos analizar usando nuestro screener de trading. Estos tickers servirán como base para recuperar datos históricos de precios, aplicar indicadores y, en última instancia, buscar oportunidades de trading potenciales.

tickers = [ 'AAPL','TSLA','AMZN','NVDA','INTC','MSFT','GOOG','META','TSM','JPM','WMT','V','XOM','MA','BA','IBM']

Paso 3: Obtención de datos del mercado

En este paso, mediante este código vamos a recuperar datos para cada símbolo de ticker en la lista de tickers. Iteramos a través de la lista y realizamos las siguientes acciones para cada ticker:

Creamos una instancia de la clase TA_Handler de la biblioteca tradingview_ta. Este manejador nos permite interactuar con las funcionalidades de análisis técnico de TradingView.

También, especificamos los parámetros para la instancia de TA_Handler:

  • simbolo: El símbolo de ticker para el cual queremos recuperar datos.
  • screener: La región o bolsa de valores desde la cual queremos obtener datos. En este caso, lo configuramos como “america” para centrarnos en acciones americanas.
  • exchange: La bolsa de valores específica donde está listado el ticker. Inicialmente buscamos datos en el NYSE (Bolsa de Valores de Nueva York).
  • interval: El intervalo de tiempo de los datos que queremos recuperar. Aquí, lo configuramos en “1d” para datos diarios.

Utilizamos el método get_analysis().summary para recuperar un resumen del análisis técnico para el ticker especificado. Este resumen contiene varios indicadores y métricas calculadas en función de los datos históricos de precios. Luego, agregamos los datos recuperados para el ticker a la lista tickers_data.

Si ocurre una excepción durante el proceso de recuperación, indicando que no se encuentran datos para el ticker en el NYSE, se maneja la excepción y se buscan los datos en el NASDAQ (Bolsa de Valores NASDAQ), que es otra bolsa de valores popular en EE.UU.

Finalmente, se imprime un mensaje indicando que los datos se han importado con éxito.

Al ejecutar este código, recopilamos datos de análisis técnico para cada ticker de las bolsas de valores especificadas. Estos datos se utilizarán posteriormente para aplicar indicadores, buscar oportunidades de trading y generar perspectivas en nuestro screener de trading.

tickers_data = []

# Iterar a través de cada ticker
for ticker in tickers:
    try:
        # Obtener datos del ticker directamente de NYSE
        data = TA_Handler(
            symbol=ticker,
            screener="america",
            exchange="NYSE",
            interval="1d"
        )
        data = data.get_analysis().summary
        tickers_data.append(data)
        
    except Exception as e:
        # Si no se encuentran datos para el ticker en NYSE, busque en NASDAQ
        print(f"No se encontraron datos del ticker {ticker} en NYSE. Buscando en NASDAQ...")
        data = TA_Handler(
            symbol=ticker,
            screener="america",
            exchange="NASDAQ",
            interval="1d"
        )
        data = data.get_analysis().summary
        tickers_data.append(data)

print("Datos importados exitosamente.")

Después de obtener los datos para todos los tickers, procedemos a procesarlos y analizarlos para extraer la información relevante con el fin de crear un gráfico con indicadores de compra, venta y neutral.

Paso 4. Procesamiento de datos obtenidos

Ahora iteramos a través de cada elemento en la lista tickers_data, que contiene los datos analizados para cada ticker. Extraemos la información específica que necesitamos, como las recomendaciones, valores de compra, venta y neutral, y los almacenamos en listas separadas.

Luego, se crea un diccionario llamado data para organizar la información extraída, asociándola con el símbolo de ticker correspondiente. Este diccionario se utiliza para crear un DataFrame de Pandas llamado df, donde cada columna representa una pieza específica de información: Ticker, Recomendaciones, Compras, Ventas y Neutrales.

#Procesado de los datos----------------------------------------------------------------------
recomendaciones = []
compras = []
ventas = []
neutrales = []

# Iterar a través de todos los datos en tickers_data
for data in tickers_data:
    recomendacion = data.get('RECOMMENDATION')
    compra = data.get('BUY')
    venta = data.get('SELL')
    neutral = data.get('NEUTRAL')
    
    recomendaciones.append(recomendacion)
    compras.append(compra)
    ventas.append(venta)
    neutrales.append(neutral)

data = {
    'Ticker': tickers,
    'Recomendaciones': recomendaciones,
    'Compras': compras,
    'Ventas': ventas,
    'Neutrales': neutrales
}

df = pd.DataFrame(data)

Para establecer un orden para las recomendaciones, definimos un diccionario llamado order_categories, que asigna valores numéricos a cada categoría. La columna Orden se crea en el DataFrame al mapear los valores de la columna Recomendaciones a las categorías correspondientes en el diccionario order_categories. Luego, el DataFrame se ordena en función de la columna Order en orden ascendente, asegurando un orden lógico de las recomendaciones.

Finalmente, se elimina la columna Orden del DataFrame ya que no es necesaria, y se muestra el DataFrame ordenado, presentando la información en un formato tabular.

Al procesar y analizar los datos de esta manera, podemos obtener perspectivas valiosas sobre las recomendaciones y categorizaciones para cada ticker, ayudándonos a tomar decisiones de trading informadas.

# Definir el orden de las categorías
order_categories = {
    'COMPRA_FUERTE': 5,
    'COMPRA': 4,
    'NEUTRAL': 3,
    'VENTA': 2,
    'VENTA_FUERTE': 1
}

# Asignar un valor numérico a cada categoría en una nueva columna "Orden"
df['Orden'] = df['Recomendaciones'].map(order_categories)
df = df.sort_values('Orden', ascending=True).reset_index(drop=True)

# Omitir la columna "Orden" si no es necesaria en el resultado final
df = df.drop('Orden', axis=1)

# Mostrar el marco de datos ordenado
print(df)

recomendaciones acciones python

Paso 5: Graficado de los datos

Podemos representar visualmente las recomendaciones mediante un gráfico de barras horizontales usando Matplotlib. Esto nos permite mostrar las señales de compra, venta y neutral para cada ticker de manera clara e intuitiva.

En el fragmento de código, comenzamos definiendo los colores para las barras, el fondo y los elementos de texto para crear un estilo visual atractivo. Luego, creamos los objetos de figura y ejes, especificando el tamaño del gráfico. El color de fondo del gráfico se establece para mejorar la presentación general.

Se incluyen anotaciones para especificar la recomendación para cada ticker. Estas anotaciones aparecen adyacentes a la barra correspondiente, proporcionando contexto adicional. Se eliminan las líneas de cuadrícula horizontales para despejar el gráfico y centrar la atención en los elementos esenciales.

#Trazado de los datos-----------------------------------------------------------------------------------------
# Crea la figura y los ejes
fig, ax = plt.subplots(figsize=(10, 6))
fig.set_facecolor('#111111')
ax.set_facecolor('#111111')

# Agregue las barras horizontales para compras, neutrales y ventas.
ax.barh(df.index, df["Compras"], height=0.25, color='#00BFFF', label='Indicadores que indican compra')
ax.barh(df.index, df["Neutrales"], height=0.25, color='#808080', label='Indicadores neutrales', left=df["Compras"])
ax.barh(df.index, df["Ventas"], height=0.25, color='#FFA500', label='Indicadores que indican venta', left=df["Compras"] + df["Neutrales"])

# Establecer las etiquetas de los ejes
ax.set_yticks(df.index)
ax.set_yticklabels(df["Ticker"], fontsize=8, color='white')
ax.set_xlabel('Número de indicadores', fontsize=10, color='white')

# Add title with larger font size and additional spacing
ax.set_title('Indicadores con recomendaciones de compra, venta y neutralidad por ticker', fontsize=14, color='white', pad=20)

# Agregar las anotaciones
for i, recommendation in enumerate(df["Recomendaciones"]):
    ax.annotate(recommendation, xy=(25, i), xytext=(26.5, i),
                color='white', fontsize=8, va='center', ha='left')

# Eliminar las líneas de cuadrícula horizontales
ax.yaxis.grid(False)

# Configurar los estilos
ax.tick_params(axis='x', colors='white')
ax.tick_params(axis='y', colors='white')
ax.spines['left'].set_color('white')
ax.spines['bottom'].set_color('white')
ax.spines['left'].set_linewidth(0.5)
ax.spines['bottom'].set_linewidth(0.5)
ax.spines['right'].set_visible(False)
ax.spines['top'].set_visible(False)

# Ajustar el espaciado
plt.tight_layout()

# Establezca el color del texto de la leyenda en blanco.
legend = ax.legend(loc='lower center', bbox_to_anchor=(0.5, -0.175), ncol=3, fontsize=8)
for text in legend.get_texts():
    text.set_color('#111111')

# Mostrar la trama
plt.show()

Recomendaciones de compra, venta, neutralidad, acciones

Descubrimiento de Oportunidades de Trading a través del Filtrado de Indicadores

Mientras que las señales colectivas ofrecen una perspectiva general, nuestro enfoque va más allá del análisis superficial. En la segunda sección, aprovechamos el poder de los indicadores técnicos al profundizar en sus detalles individuales. Descargamos y analizamos los puntos de datos específicos para cada indicador, lo que nos permite aplicar técnicas de filtrado avanzadas.

En el primer paso, importamos los datos de los indicadores técnicos para una lista de tickers de acciones de la bolsa NYSE o NASDAQ y los almacenamos en un DataFrame de pandas llamado df_adrs_indicators. El código itera sobre cada ticker, intenta recuperar los datos del indicador del NYSE y, si falla, busca los datos en el NASDAQ. Los datos recuperados se concatenan con el DataFrame existente. Finalmente, los nombres de las columnas se convierten en cadenas de texto y se imprime un mensaje de éxito. Este proceso permite la consolidación de datos de indicadores técnicos para múltiples acciones, facilitando el análisis adicional e identificación de oportunidades de trading.

#Oportunidades de trading mediante filtrado de señales----------------------------------

df_adrs_indicators = pd.DataFrame()

for ticker in tickers:
    try:
        data = TA_Handler(
            symbol=ticker,
            screener="america",
            exchange="NYSE",
            interval="1d"
        )
        data = data.get_analysis().indicators

    except Exception as e:
        print(f"No se encontraron datos del ticker {ticker} en NYSE. Buscando en NASDAQ...")
        data = TA_Handler(
            symbol=ticker,
            screener="america",
            exchange="NASDAQ",
            interval="1d"
        )
        data = data.get_analysis().indicators
        
    df_temp = pd.DataFrame(data, index=[ticker])
    df_adrs_indicators = pd.concat([df_adrs_indicators, df_temp])

df_adrs_indicators.columns = df_adrs_indicators.columns.astype(str)
print("Datos importados exitosamente.")

Como resultado, obtenemos el DataFrame df_adrs_indicators. Tiene 91 columnas con información sobre muchos indicadores técnicos, información extremadamente útil para filtrar los activos según los criterios que consideremos relevantes.

Por ejemplo, una vez que hemos importado los datos de los indicadores técnicos en el DataFrame df_adrs_indicators, podemos proceder a filtrar las acciones basándonos en criterios específicos. En este fragmento de código, aplicamos varios filtros para identificar acciones que cumplan ciertas condiciones.

Primero, filtramos las acciones que tienen su valor de Media Móvil Exponencial (EMA) de 10 días cruzando por encima de su EMA de 50 días. Esto se hace creando un nuevo DataFrame llamado df_filtered utilizando la condición df_adrs_indicators[‘EMA10’] > df_adrs_indicators[‘EMA20’].

Luego, afinamos aún más la selección filtrando las acciones con un valor del Índice de Fuerza Relativa (RSI) superior a 50. El DataFrame df_filtered se actualiza con esta condición: df_filtered[df_filtered[‘RSI’] > 50].

A continuación, aplicamos un filtro para las acciones con un Convergencia/Divergencia de la Media Móvil (MACD) positivo, específicamente cuando la línea MACD cruza por encima de la línea de señal. El DataFrame df_filtered se actualiza nuevamente con la condición: df_filtered[df_filtered[‘MACD.macd’] > df_filtered[‘MACD.signal’]].

Por último, filtramos las acciones con un Índice Direccional Promedio (ADX) superior a 25, indicando una tendencia fuerte. El DataFrame df_filtered se actualiza con la condición final: df_filtered[df_filtered[‘ADX’] > 25].

# Filtrar acciones con EMA10 cruzando EMA50
df_filtrado = df_adrs_indicators[df_adrs_indicators['EMA10'] > df_adrs_indicators['EMA50']]

# Filtrar acciones con RSI superior a 50 (sobrecompra)
df_filtrado = df_filtrado[df_filtrado['RSI'] > 50]

# Filtrar acciones con MACD positivo (cruce de línea de señal)
df_filtrado = df_filtrado[df_filtrado['MACD.macd'] > df_filtrado['MACD.signal']]

# Filtrar acciones con ADX por encima de un cierto umbral (lo que indica una tendencia fuerte)
df_filtered = df_filtrado[df_filtrado['ADX'] > 20]

# Imprimir las acciones que cumplen los criterios
acciones_filtradas = df_filtered.index.to_list()

print('Acciones filtradas:', acciones_filtradas)

Acciones filtradas: [‘JPM’, ‘WMT’, ‘V’, ‘MA’, ‘IBM’]

También podemos observar los movimientos de precios de las acciones filtradas usando mplfinance, una biblioteca de Python que proporciona una interfaz de alto nivel para crear gráficos y visualizaciones financieras. Está construida sobre la popular biblioteca Matplotlib y ofrece una forma conveniente de generar gráficos de velas, gráficos de líneas, gráficos de barras y otros tipos de gráficos financieros.

#Trazado de gráficos de acciones filtradas------------------------------------------------------

# Obtención de la fecha actual
fecha_final = datetime.now().strftime("%Y-%m-%d")

# Calcular la fecha de inicio (hace 3 meses a partir de hoy)
fecha_inicio = (datetime.now() - timedelta(days=3 * 30)).strftime("%Y-%m-%d")

# Calcular el número de filas y columnas según el diseño deseado
num_rows = (len(acciones_filtradas) + 1) // 2
num_cols = 2

# Crear una figura con subtramas
fig, axes = plt.subplots(nrows=num_rows, ncols=num_cols, figsize=(12, 8))
fig.suptitle("Gráficos de candelas diarios", fontsize=14)

# Iterar sobre cada acción y agregar una subparcela para cada una
for i, simbolo in enumerate(acciones_filtradas):
    # Calcular el índice de fila y columna para la subparcela actual
    row = i // num_cols
    col = i % num_cols

    # Obtención de datos históricos de Yahoo Finance
    data = yf.download(simbolo, start=fecha_inicio, end=fecha_final)

    # Dibuje el gráfico de velas en el subgráfico
    mpf.plot(data, type='candle', ax=axes[row, col], volume=False, show_nontrading=False)

    # Establecer el título de la subtrama
    axes[row, col].set_title(simbolo)

# Ajustar el espaciado entre subparcelas
plt.tight_layout()

# Show the plot
plt.show()

acciones filtradas indicadores tecnicos

 

Pueden acceder a más códigos de Python con funciones de trading interesantes en: Programas de Python Para Trading


 

 

TagsPython
Raul Canessa

Leave a reply