2015-11-30 13 views
6

Pracuję z dużym zestawem danych biologicznych.Obliczanie korelacji parami między wszystkimi kolumnami

Chcę obliczyć PCC (współczynnik korelacji Pearsona) wszystkich kombinacji 2-kolumnowych w mojej tabeli danych i zapisać wynik jako DataFrame lub plik CSV.

Tabela danych wygląda następująco: kolumny to nazwa genów, a wiersze to kod zbioru danych. Liczby zmiennoprzecinkowe oznaczają, ile gen jest aktywowany w zbiorze danych.

 GeneA GeneB GeneC ... 
DataA 1.5 2.5 3.5 ... 
DataB 5.5 6.5 7.5 ... 
DataC 8.5 8.5 8.5 ... 
... 

jako wyjście, chcę zbudować tabelę (DataFrame lub pliku CSV), jak poniżej, ponieważ scipy.stats.pearsonr funkcja zwraca (PCC, p-value). W moim przykładzie XX i YY oznaczają wyniki pearsonr ([1.5, 5.5, 8.5], [2.5, 6.5, 8.5]). W ten sam sposób ZZ i AA oznaczają wynik pearsonr ([1,5, 5,5, 8,5], [3,5, 7,5, 8,5]). Nie potrzebuję zbędnych danych, takich jak GeneB_GeneA lub GeneC_GeneB w moim teście.

   PCC P-value 
GeneA_GeneB XX YY 
GeneA_GeneC ZZ AA 
GeneB_GeneC BB CC 
... 

Ponieważ liczba kolumn i wierszy jest duża (ponad 100), a ich nazwy są skomplikowane, użycie nazw kolumn lub nazw wierszy będzie trudne.

Może to być prosty problem dla ekspertów, nie wiem jak sobie z tym poradzić w bibliotece Pythona i Pandy. Szczególnie tworzenie nowych DataFrame i dodawanie wyników wydaje się być bardzo trudne.

Przepraszamy za moje słabe wyjaśnienie, ale mam nadzieję, że ktoś mógłby mi pomóc.

+0

Odpowiedziano tutaj: [link] (http://stackoverflow.com/questions/3949226/calculating-pearson-correlation-and-simnificance-in-python) – Glostas

+0

Dziękuję za komentarz. Myślę, że tytuł nie był wystarczająco dobry. To, co chcę wiedzieć, to nie to, jak obliczyć PCC, ale obliczać PCC wszystkich par kolumn i zapisać wyniki jako nową ramkę DataFrame. – z991

Odpowiedz

8
from pandas import * 
import numpy as np 
from libraries.settings import * 
from scipy.stats.stats import pearsonr 
import itertools 

Tworzenie dane losowe próbki:

df = DataFrame(np.random.random((5, 5)), columns=['gene_' + chr(i + ord('a')) for i in range(5)]) 
print(df) 

    gene_a gene_b gene_c gene_d gene_e 
0 0.471257 0.854139 0.781204 0.678567 0.697993 
1 0.292909 0.046159 0.250902 0.064004 0.307537 
2 0.422265 0.646988 0.084983 0.822375 0.713397 
3 0.113963 0.016122 0.227566 0.206324 0.792048 
4 0.357331 0.980479 0.157124 0.560889 0.973161 

correlations = {} 
columns = df.columns.tolist() 

for col_a, col_b in itertools.combinations(columns, 2): 
    correlations[col_a + '__' + col_b] = pearsonr(df.loc[:, col_a], df.loc[:, col_b]) 

result = DataFrame.from_dict(correlations, orient='index') 
result.columns = ['PCC', 'p-value'] 

print(result.sort_index()) 

        PCC p-value 
gene_a__gene_b 0.461357 0.434142 
gene_a__gene_c 0.177936 0.774646 
gene_a__gene_d -0.854884 0.064896 
gene_a__gene_e -0.155440 0.802887 
gene_b__gene_c -0.575056 0.310455 
gene_b__gene_d -0.097054 0.876621 
gene_b__gene_e 0.061175 0.922159 
gene_c__gene_d -0.633302 0.251381 
gene_c__gene_e -0.771120 0.126836 
gene_d__gene_e 0.531805 0.356315 
  • Get unikalne kombinacje DataFrame kolumn za pomocą itertools.combination(iterable, r)
  • iterację tych kombinacji w parach i obliczania korelacji przy użyciu scipy.stats.stats.personr
  • Dodaj wyniki (PCC i p-wartość krotki) do dictionary
  • produkcji DataFrame z dictionary

Następnie można również zapisać result.to_csv(). Może się okazać, że wygodnie jest użyć MultiIndex (dwie kolumny zawierające nazwy poszczególnych kolumn) zamiast nazw utworzonych dla korelacji parami.

+0

Dziękuję bardzo!Jak sobie radziliście z ChenZhongPu, używanie funkcji kombinacji wydaje się dobrym rozwiązaniem dla tego rodzaju problemu. Chciałbym jeszcze raz jeszcze podziękować za uprzejme wyjaśnienia. To było bardzo pomocne, ponieważ jestem nowy w Pythonie. – z991

2

Aby uzyskać pary, jest to problem o numerze combinations. Możesz concat wszystkie wiersze w jeden wynik dataframe.

from pandas import * 
from itertools import combinations 
df = pandas.read_csv('gene.csv') 
# get the column names as list, which are gene names 
column_list = df.columns.values.tolist() 
result = [] 
for c in combinations(column_list, 2): 
    firstGene, secondGene = c 
    firstGeneData = df[firstGene].tolist() 
    secondGeneData = df[secondGene].tolist() 
    # now to get the PCC, P-value using scipy 
    pcc = ... 
    p-value = ... 
    result.append(pandas.DataFrame([{'PCC': pcc, 'P-value': p-value}], index=str(firstGene)+ '_' + str(secondGene), columns=['PCC', 'P-value']) 

result_df = pandas.concat(result) 
#result_df.to_csv(...) 
+0

Nie wiedziałem o "kombinacjach", ale wygląda miło, gdy wykonuję tego rodzaju obliczenia pary. Nauczyłem się również, że tworzenie DataFrame z listy może być łatwo przekazywane przez funkcję concat. Dziękuję Ci bardzo! – z991

Powiązane problemy