Как я могу я группировать электронные письма доменом, объединенным и итоговым из всех файлов в каталоге?

У меня есть некоторые файлы CSV. Каждый файл имеет список адресов электронной почты. Следующее является извлеченными данными из файла:

%%%%%%%%%%@yahoo.com
%%%%%%@wanadoo.fr
%%%%raviplywoodglasscentre@yahoo.comravi
%%nameemail%%@yahoo.com
%.getincontact@numberland.com
%1%3@example.com
%1@example.com

То, чего я пытаюсь делать попытку, извлекает домены из них адрес электронной почты и затем располагает адреса электронной почты таким способом, что электронные письма, связанные с определенным доменом, перечислены вместе.
Например:

yahoo.com,%%%%%%%%%%@yahoo.com
wanadoo.fr,%%%%%%@wanadoo.fr
yahoo.comravi,%%%%raviplywoodglasscentre@yahoo.comravi
yahoo.com,%%nameemail%%@yahoo.com
numberland.com,%.getincontact@numberland.com
example.com,%1%3@example.com
example.com,%1@example.com

Окончательный результат, который я пытаюсь получить, похож на следующее:

yahoo.com,%%%%%%%%%%@yahoo.com,%%nameemail%%@yahoo.com
wanadoo.fr,%%%%%%@wanadoo.fr
yahoo.comravi,%%%%raviplywoodglasscentre@yahoo.comravi
numberland.com,%.getincontact@numberland.com
example.com,%1%3@example.com,%1@example.com
3
задан 25 January 2017 в 16:14

3 ответа

Python путь, с помощью itertools' groupby():

1. Запишите вывод на файл (всех файлов в каталоге) в терминале

N.B. следите за этим, терминал показывает ограниченное количество строк

#!/usr/bin/env python3
from operator import itemgetter
from itertools import groupby
import os
import sys

dr = sys.argv[1]

for f in os.listdir(dr):
    lines = [[l.strip(), l.split("@")[-1].strip()] for l in \
             open(os.path.join(dr, f)).readlines()]
    lines.sort(key=itemgetter(1))
    for item, occurrence in groupby(lines, itemgetter(1)):
        func = [s[0] for s in list(occurrence)]; print(item+","+",".join(func))

Использовать

  1. Скопируйте сценарий в пустой файл, сохраните его как group_domains.py
  2. Выполните его с целенаправленным каталогом как аргумент:

    python3 /path/to/group_domains.py /directory/with/files
    

Вывод будет похож:

example.com,%1%3@example.com,%1@example.com
numberland.com,%.getincontact@numberland.com
wanadoo.fr,%%%%%%@wanadoo.fr
yahoo.com,%%%%%%%%%%@yahoo.com,%%nameemail%%@yahoo.com
yahoo.comravi,%%%%raviplywoodglasscentre@yahoo.comravi

Примечания

Как это, сценарий создает вывод на файл в терминале. Мы могли легко объединиться (суммируют) вывод (выводы) отдельных файлов и впоследствии пишут сгруппированный результат в файл и т.д., но упомяните.

Объяснение

В понятии:

  1. Строки файла читаются и разделяются для чтения домена
  2. Созданный список впоследствии отсортирован по домену:

    lines.sort(key=itemgetter(1))
    
  3. и сгруппированный доменом:

    groupby(lines, itemgetter(1))
    

Результат (строка) сделан из объекта (домен) и его "участники".

2. Напишите отчет на файл (снова всех файлов в каталоге) в переименованные файлы.

Сценарий ниже запишет вывод в переименованный файл, использование является тем же:

#!/usr/bin/env python3
from operator import itemgetter
from itertools import groupby
import os
import sys

dr = sys.argv[1]


for f in os.listdir(dr):
    write = []
    file = os.path.join(dr, f)
    lines = [[l.strip(), l.split("@")[-1].strip()] for l in open(file).readlines()]
    lines.sort(key=itemgetter(1))
    for item, occurrence in groupby(lines, itemgetter(1)):
        func = [s[0] for s in list(occurrence)]
        write.append(item+","+",".join(func))
    open(os.path.join(dr, "grouped_"+f), "wt").write("\n".join(write))

из файла как:

some_list.txt

это создаст переименованный:

grouped_some_list.txt

Использовать

просто:

python3 /path/to/group_domains.py /directory/with/files

3. Напишите отчет (сводка) на целом каталоге в единственный файл

Версия ниже будет суммировать все домены в файлах в каталоге. Отчет сохраняется в файле, для установки как второй аргумент.

#!/usr/bin/env python3
from operator import itemgetter
from itertools import groupby, chain
import os
import sys

dr = sys.argv[1]
outfile = sys.argv[2]

report = []

for f in os.listdir(dr):
    lines = [[l.strip(), l.split("@")[-1].strip()] for l in \
             open(os.path.join(dr, f)).readlines()]
    lines.sort(key=itemgetter(1))
    for item, occurrence in groupby(lines, itemgetter(1)):
        func = [s[0] for s in list(occurrence)]
        report.append([item, func])

report.sort(key=itemgetter(0))

with open(outfile, "wt") as out:
    for item, occurrence in groupby(report, itemgetter(0)):
        func = [item for sublist in [it[1] for it in list(occurrence)] for item in sublist]
        out.write(item+","+",".join(func)+"\n")

Использовать

  1. Скопируйте сценарий в пустой файл
  2. Выполнение это:

    python3 /path/to/group_domains.py /directory/with/files /path/to/outputfile.txt
    

    (или безотносительно расширения)

Примечания

Последняя версия будет сначала подводить итог на файл, как упомянуто в вопросе, и дополнительно суммировать все файлы в выходной файл, где подобные домены из отдельных файлов будут объединены в одну строку на домен.

6
ответ дан 1 December 2019 в 13:01

Используя awk:

awk -F, '{a[$1] = a[$1]","$2} END {for (i in a) print i a[i]}'

вывод не находится ни в каком конкретном порядке:

$ awk -F, '{a[$1] = a[$1]","$2} END {for (i in a) print i a[i]}' foo
yahoo.comravi,%%%%raviplywoodglasscentre@yahoo.comravi
yahoo.com,%%%%%%%%%%@yahoo.com,%%nameemail%%@yahoo.com
numberland.com,%.getincontact@numberland.com
example.com,%1%3@example.com,%1@example.com
wanadoo.fr,%%%%%%@wanadoo.fr
2
ответ дан 1 December 2019 в 13:01

Вот a perl версия, с помощью хеша анонимных массивов:

$ perl -F@ -alne '
    push @{ $h{$F[1]} }, $_ }{ 
    for $k (reverse sort keys %h) {print join ",", $k, @{ $h{$k} }
  }' emails.csv
yahoo.comravi,%%%%raviplywoodglasscentre@yahoo.comravi
yahoo.com,%%%%%%%%%%@yahoo.com,%%nameemail%%@yahoo.com
wanadoo.fr,%%%%%%@wanadoo.fr
numberland.com,%.getincontact@numberland.com
example.com,%1%3@example.com,%1@example.com

Порядок не точно, что Вы попросили

5
ответ дан 1 December 2019 в 13:01

Другие вопросы по тегам:

Похожие вопросы: