In [1]:
from gensim.utils import simple_preprocess
from gensim import corpora, models, similarities

from os import listdir

In [2]:
""" 
os textos de cada classes estão divididos em
subdiretórios dentro de path
"""
class MyCorpus(object):
    
    def __init__(self,path):
        self.path = path
        self.klasses = self.file_ids_klass()
        self.dictionary = corpora.Dictionary(self.get_text(fname) for fname in self.klasses.keys())
        
    def __iter__(self):
        for fname in self.klasses.keys():
            yield self.dictionary.doc2bow(self.get_text(fname))
            
    def text_bow(self,fname):
        return self.dictionary.doc2bow(self.get_text(fname))
    
    def file_ids_klass(self):
        ids = {}
        for klass in listdir(self.path):
            for fname in listdir(self.path+'/'+klass):
                ids[klass+'/'+fname] = klass
        return ids
                
    def get_text(self,fname):
        with open(self.path+'/'+fname) as finput:
            text = ''.join(finput.readlines())
            return self.pre_process(text)
    
    """
        por hora, um preprocessamento simples...
        podemos trocar por um mais elaborado depois
    """
    def pre_process(self,text):
        return simple_preprocess(text)

In [3]:
mc = MyCorpus('/home/kadnoise/Downloads/review_polarity/txt_sentoken/')

In [ ]:


In [ ]:
# gera o modelo tf-idf
tfidf = models.TfidfModel(mc)

In [ ]:
# cria um grafo dirigido (Digrafo)
import networkx as nx

G = nx.DiGraph()

# cada texto é um nó do grafo
# a classe do texto é um atributo do nó do grafo
for k,v in mc.klasses.items():
    G.add_node(k,klass=v)

In [ ]:
# adiciona as arestas no grafo

# nomes dos arquivos...
# variável auxiliar...
names = mc.klasses.keys()


# gera o modelo de similaridades
# para encontaros k-vizinhos de cada nó
# num_best é o número de k-vizinhos + 1 (pois o nó é vizinho dele mesmo)
# num_best=11 gera um grafo com 10 vizinhos pra cada nó

index = similarities.Similarity('tmp',tfidf[mc],num_features=len(mc.dictionary.keys()),num_best=11)

for k in names:
    for nn in index[tfidf[mc.text_bow(k)]]:
        if not k==names[nn[0]]:
            G.add_edge(k,names[nn[0]],weight=nn[1])

In [ ]:
# calcula a distribuição do grau de cada nó

from collections import Counter

# como o out_degree é sempre 10 (por construção)
# basta usar o in_degree
degree = G.in_degree().values()
cdegree = Counter(degree)

In [ ]:
# skewness and kurtosis mede o quanto não uniforme é a distribuição

from scipy.stats import skew, kurtosis

print skew(degree), kurtosis(degree)

In [ ]:
%matplotlib inline
import matplotlib.pyplot as plt

In [ ]:
plt.plot(cdegree.keys(),cdegree.values(),'bo-')

In [ ]:
good_bad_edges = {}

for k in names:
    good_bad_edges[k] = {}
    good_bad_edges[k]['good'] = 0
    good_bad_edges[k]['bad'] = 0
    good_bad_edges[k]['all'] = 0
    for edge in G.in_edges(k):
        if G.node[edge[0]]['klass'] == G.node[edge[1]]['klass']:
            good_bad_edges[k]['good']+=1
        else:
            good_bad_edges[k]['bad']+=1
        good_bad_edges[k]['all']+=1

In [ ]:
baddegree = [d['bad'] for d in good_bad_edges.values()]
CBad = Counter(baddegree)

In [ ]:
plt.plot(cdegree.keys(),cdegree.values(),'bo-')
plt.plot(CBad.keys(),CBad.values(),'ro-')

In [ ]:
print skew(baddegree), kurtosis(baddegree)

In [ ]:
from scipy.stats import spearmanr,pearsonr
import numpy as np

corr = np.array([[d['bad'], d['all']] for d in good_bad_edges.values()])

print spearmanr(corr[:,0],corr[:,1]), pearsonr(corr[:,0],corr[:,1])

In [ ]:
import numpy as np
color = ['r' if node[1]['klass'] == 'positive' else 'b' for node in G.nodes(data=True)]

pos = nx.spring_layout(G)


ec = nx.draw_networkx_edges(G, pos, alpha=0.01)
nc = nx.draw_networkx_nodes(G, pos, node_color=color, node_size=2**np.sqrt(np.array(degree)),alpha=0.3)

In [ ]: