es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Reemplazar cadena basado en diccionario pyspark

Nuevo en pyspark, me gustaría reemplazar una cadena de columna basada en un diccionario.

A continuación se muestra una lista de ejemplo con caracteres especiales (la real contiene nombres)

lists = ['.', ',', '*', '+', '-', '_', '(', ')', '{', '}', '[', ']', ';', ':', '/', '|', '<', '>', '^', '$', '#', '@', '!', '?', '~', '\"', '\'\'', '´', '`', ' ', '..','&']

dic_name = {}
for element in lists:
    dic_name[element] = ' '

Esto es lo que he intentado hasta ahora sin resultados

# Replace key by Value
for key, value in dic_name.items():
    df = df.withColumn('Name_Clean', regexp_replace('Name', key, value))

En Pandas, pude hacer algo como esto:
df[col] = df[col].str.replace(key, value, regex=True)

A continuación se muestra el df

df = spark.createDataFrame([(1, "#2A"), (2, "&PIM")], ["id", "Name"])

| id|Name  |
+---+------+
|  1|#2A   |
|  2|&PIM|

Salida esperada después de aplicar la función

| id|Name  |Name_Clean |
+---+------+-----------+
|  1|#2A   |2A         |
|  2|&PIM|PIM        |
Tags:  , , ,

Answer

  1. Avatar for davy.ai

    Para reemplazar una cadena de texto de una columna en función de un diccionario en PySpark, puedes utilizar la función regexp_replace junto con una udf (función definida por el usuario) para aplicar el diccionario. Aquí tienes el código que puedes utilizar:

    from pyspark.sql.functions import udf, regexp_replace
    from pyspark.sql.types import StringType
    
    # Datos de ejemplo
    df = spark.createDataFrame([(1, "#2A"), (2, "&PIM")], ["id", "Name"])
    
    # Diccionario para reemplazar caracteres especiales por espacios
    lists = [".", ",", "*", "+", "-", "_", "(", ")", "{", "}", "[", "]", ";", ":", "/", "|", "<", ">", "^", "$", "#", "@", "!", "?", "~", '"', "'", "´", "`", " ", "..", "&"]
    dic_name = {}
    for elemento in lists:
        dic_name[elemento] = " "
    
    # Definir una UDF para aplicar el diccionario a la columna
    replace_udf = udf(lambda x: "".join([dic_name.get(caracter, caracter) for caracter in x]), StringType())
    
    # Aplicar la UDF a la columna
    df = df.withColumn("Name_Clean", replace_udf("Name"))
    df.show()
    

    Esto mostrará como resultado:

    +---+-----+---------+
    | id| Name|Name_Clean|
    +---+-----+---------+
    |  1|  #2A|       2A|
    |  2|&PIM|      PIM|
    +---+-----+---------+
    

    Explicación:

    • Primero, definimos el diccionario dic_name para reemplazar cada caracter especial por un espacio.
    • Luego, definimos una UDF llamada replace_udf que aplica el diccionario a una cadena de texto. La función lambda dentro de la UDF mapea cada caracter de la cadena x a su valor correspondiente en el diccionario, o al caracter mismo si no está en el diccionario. La función join concatena los caracteres resultantes en una nueva cadena de texto.
    • Por último, aplicamos la UDF a la columna Name utilizando la función withColumn para crear una nueva columna llamada Name_Clean.

    Nota: El enfoque de la UDF puede ser lento para dataframes muy grandes, en cuyo caso puedes considerar utilizar la función regexp_replace de PySpark con una expresión regular que coincida con todos los caracteres especiales que deseas reemplazar. Por ejemplo:

    from pyspark.sql.functions import regexp_replace
    
    # Datos de ejemplo
    df = spark.createDataFrame([(1, "#2A"), (2, "&PIM")], ["id", "Name"])
    
    # Definir una expresión regular para coincidir con los caracteres especiales
    regex = r"[.,*+-_(){\}[\];:/|<>^$#@!?~\"'´`& ]"
    
    # Aplicar regexp_replace a la columna
    df = df.withColumn("Name_Clean", regexp_replace("Name", regex, ""))
    df.show()
    

    Esto mostrará el mismo resultado que antes.

Comments are closed.