Сортировать / выровнять столбцы данных таким образом, чтобы значения строк соответствовали столбцу основного списка, если в столбце нет совпадений. 0 - PullRequest
1 голос
/ 11 октября 2019

Я хочу отсортировать фрейм данных (3106 строк х 24 столбца) на основе основного списка строк в первом столбце («MASTER»), чтобы строки в каждой строке фрейма данных были выровнены при совпадении иесли совпадения нет, выведите 0 для этой ячейки. Главный список содержит все возможные строки в любом столбце, но не каждая строка будет отображаться в каждом столбце.

Этот пост SO довольно близок к тому, что я пытаюсь сделать:

Выровняйте DataFrames в пандах так, чтобы данные соответствовали строкам

. Я попытался использовать этот подход и понял, что он просто смотрит, соответствует ли каждая строка совпадению на основе порядка в главном столбце, но не выполняет поисквесь столбец для совпадения или переупорядочения.

new_data = data[data.apply(lambda x: x['MASTER'] == x, axis=1)]

Вот что я пытаюсь выполнить с моими данными.

ДО

MASTER         CENTRAL_NERVOUS  NERVOUS_SYSTEM  NEUROGENESIS
12AEX          9630013A20RIK    12AEX           2610301B20RIK
2610042L04RIK  AARS             2610042L04RIK   9630013A20RIK
2610301B20RIK  AATK             2610301B20RIK   A830010M20RIK
2700046G09RIK  ABCA2            2700046G09RIK   AU040320
31BEX          ABCB1B           31BEX           AATK
38DLP          ABCB6            7A6EX           ABCA2
7A6EX          ABL1             9630013A20RIK   ABCC8
9630013A20RIK  ABL2             97C2            ABI1
97C2           ABR              A830010M20RIK   ABI2
...            ...              ...             ...

ПОСЛЕ

MASTER         CENTRAL_NERVOUS  NERVOUS_SYSTEM  NEUROGENESIS
12AEX          0                12AEX           0
2610042L04RIK  0                2610042L04RIK   0
2610301B20RIK  0                2610301B20RIK   2610301B20RIK
2700046G09RIK  0                2700046G09RIK   0
31BEX          0                31BEX           0
38DLP          0                0               0
7A6EX          0                7A6EX           0
9630013A20RIK  9630013A20RIK    9630013A20RIK   9630013A20RIK
97C2           0                97C2            0

Я пытался сделать это с pandas / python, но был бы открыт для решений w / awk / bash или R. Любые подсказки / будущие указания приветствуются, так как я застрял в этой точке.

Ответы [ 2 ]

1 голос
/ 11 октября 2019

IIUC вы можете использовать applymap или apply в Pandas. Я не уверен насчет порядка сортировки в вашем примере.

df[df.applymap(lambda x: x in df.MASTER.tolist())].fillna(0)

или

df[df.apply(lambda col: col.isin(df.MASTER))].fillna(0)

Результат:

|   | MASTER        | CENTRAL_NERVOUS | NERVOUS_SYSTEM | NEUROGENESIS  |
|---|---------------|-----------------|----------------|---------------|
| 0 | 12AEX         | 9630013A20RIK   | 12AEX          | 2610301B20RIK |
| 1 | 2610042L04RIK | 0               | 2610042L04RIK  | 9630013A20RIK |
| 2 | 2610301B20RIK | 0               | 2610301B20RIK  | 0             |
| 3 | 2700046G09RIK | 0               | 2700046G09RIK  | 0             |
| 4 | 31BEX         | 0               | 31BEX          | 0             |
| 5 | 38DLP         | 0               | 7A6EX          | 0             |
| 6 | 7A6EX         | 0               | 9630013A20RIK  | 0             |
| 7 | 9630013A20RIK | 0               | 97C2           | 0             |
| 8 | 97C2          | 0               | 0              | 0             |

И если вы хотите, чтобы строки были отсортированы поMASTER затем используйте ниже вместо apply.

dfs = np.split(df,len(df.columns), axis=1)
dfs = [df.set_index(df.columns[0], drop=False) for df in dfs]
dfs[0].join(dfs[1:]).reset_index(drop=True).fillna(0)

Результат:

|   | MASTER        | CENTRAL_NERVOUS | NERVOUS_SYSTEM | NEUROGENESIS  |
|---|---------------|-----------------|----------------|---------------|
| 0 | 12AEX         | 0               | 12AEX          | 0             |
| 1 | 2610042L04RIK | 0               | 2610042L04RIK  | 0             |
| 2 | 2610301B20RIK | 0               | 2610301B20RIK  | 2610301B20RIK |
| 3 | 2700046G09RIK | 0               | 2700046G09RIK  | 0             |
| 4 | 31BEX         | 0               | 31BEX          | 0             |
| 5 | 38DLP         | 0               | 0              | 0             |
| 6 | 7A6EX         | 0               | 7A6EX          | 0             |
| 7 | 9630013A20RIK | 9630013A20RIK   | 9630013A20RIK  | 9630013A20RIK |
| 8 | 97C2          | 0               | 97C2           | 0             |
1 голос
/ 11 октября 2019

Мы можем использовать lapply и match в R

df[-1] <- lapply(df[-1], function(x) x[match(df$MASTER, x)])
#If need to change to 0 or by default it is NA
df[is.na(df)] <- 0


#         MASTER CENTRAL_NERVOUS NERVOUS_SYSTEM  NEUROGENESIS
#1         12AEX               0          12AEX             0
#2 2610042L04RIK               0  2610042L04RIK             0
#3 2610301B20RIK               0  2610301B20RIK 2610301B20RIK
#4 2700046G09RIK               0  2700046G09RIK             0
#5         31BEX               0          31BEX             0
#6         38DLP               0              0             0
#7         7A6EX               0          7A6EX             0
#8 9630013A20RIK   9630013A20RIK  9630013A20RIK 9630013A20RIK
#9          97C2               0           97C2             0

и аналогично, используя dplyr

library(dplyr)
df %>% mutate_at(-1, ~.[match(MASTER, .)]) 

data

Если вы хотите преобразовать значения в 0, убедитесь, что столбцы являются символами, а не факторами.

df <- structure(list(MASTER = c("12AEX", "2610042L04RIK", "2610301B20RIK", 
"2700046G09RIK", "31BEX", "38DLP", "7A6EX", "9630013A20RIK", 
"97C2"), CENTRAL_NERVOUS = c("9630013A20RIK", "AARS", "AATK", 
"ABCA2", "ABCB1B", "ABCB6", "ABL1", "ABL2", "ABR"), NERVOUS_SYSTEM = c("12AEX", 
"2610042L04RIK", "2610301B20RIK", "2700046G09RIK", "31BEX", "7A6EX", 
"9630013A20RIK", "97C2", "A830010M20RIK"), NEUROGENESIS = c("2610301B20RIK", 
"9630013A20RIK", "A830010M20RIK", "AU040320", "AATK", "ABCA2", 
"ABCC8", "ABI1", "ABI2")), class = "data.frame", row.names = c(NA, -9L))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...