У меня есть таблица в Hadoop, которая содержит 7 миллиардов строк, которые могут содержать что угодно. Мне нужно удалить каждое имя из столбца, содержащего строки. Пример строки: «Джон пошел в парк», и мне нужно удалить из него «Джон», в идеале просто заменить на «[имя]».
В случае «Джон и Мэри вышли на рынок», результатом будет «[ИМЯ], а [ИМЯ] - на рынок».
Для поддержки этого у меня есть упорядоченный список наиболее часто встречающихся имен по 20 тысяч китов.
У меня есть доступ к Hue (Hive, Impala) и Zeppelin (Spark, Python и библиотеки) для выполнения этого.
Я пробовал это в БД, но неспособность обновить столбцы или перебрать переменную сделала ее незапускаемой, поэтому использование Python и PySpark кажется лучшим вариантом, особенно с учетом количества вычислений (20 тыс. Имен * 7bil входные строки)
#nameList contains ['John','Emma',etc]
def removeNames(line, nameList):
str_line= line[0]
for name in nameList:
rx = f"(^| |[[:^alpha:]])({name})( |$|[[:^alpha:]])"
str_line = re.sub(rx,'[NAME]', str_line)
str_line= [str_line]
return tuple(str_line)
df = session.sql("select free_text from table")
rdd = df.rdd.map(lambda line: removeNames(line, nameList))
rdd.toDF().show()
Код выполняется, но он занимает полтора часа, даже если я ограничиваю входной текст 1000 строками (что для Spark - ничто), и строки в действительности не заменяются.
Что меня интересует, так это: почему карта фактически не обновляет строки RDD, и как я могу сделать это более эффективным, чтобы оно выполнялось за разумное время?
Это моя первая публикация, так что если пропущена необходимая информация, я внесу столько, сколько смогу.
Спасибо!