def _query_survey(data, uu_volume = 0.01, upper_limit_of_lower_dic = 30, lower_criteria = 0.5, upper_criteria = 0.7, link_criteria = 0.4, img_criteria = 0.2, script_criteria = 0.2): #クエリパラメータの種類を把握する query_ids = {} for h, s in data.items(): for state, v in s.items(): if v['is_state'] == True: #stateとして採用されているもの限定にする #クエリパラメータのkeyとvalueの種類を整理する for q in v['query_list']: ids = q.split('&') for id in ids: kvs = id.split('=') if len(kvs) >= 2: query_ids.setdefault(kvs[0], []) query_ids[kvs[0]].append(kvs[1]) else: query_ids.setdefault(kvs[0], []) query_ids[kvs[0]].append('') for id, p in query_ids.items(): #重複要素の除去 query_ids[id] = list(set(query_ids[id])) #2からmax個までのパラメータの値があるクエリのみ、詳細を調べて差異がある場合にはstateとして分類する for id, p in query_ids.items(): if len(p) >= 2 and len(p) <= upper_limit_of_lower_dic: #各keyに対してvalueの種類ごとにクロールするURLを一個だけpick-upする url = {} for value in p: param = id + '=' + value num = 0 state_id, target_url = None, None for q in v['query_list']: if q.find(param) >= 0: num += 1 if num == 1: state_id = state + '?' + param target_url = state + '?' + q #一定数のuuボリュームがあるクエリパラメータだけクローリング対象のstateとして採用する rate = float(num) / float(v['netloc_uu']) if v['netloc_uu'] != 0 else 0 if rate >= uu_volume and state_id != None: url.setdefault(state_id, target_url) #各URLの差分を見て、差分が顕著ならどちらもstateとして採用する for sub_state0, u0 in url.items(): for sub_state1, u1 in url.items(): if sub_state0 != sub_state1: similar = contents_features.dif_html(u0, u1, lower_criteria = lower_criteria, upper_criteria = upper_criteria, link_criteria = link_criteria, img_criteria = img_criteria, script_criteria = script_criteria) if not similar: data[h][state]['query_state'].append(sub_state0) data[h][state]['query_state'].append(sub_state1) data[h][state]['query_state'] = list(set(data[h][state]['query_state'])) return data
def __adopt_query_state(query_ids, urls): adopted = [] for id, values in query_ids.items(): id2url = {} origin, num= '', 0 for value in values: #value以外のパラメータのキーパラメータは同じように選ぶようする ratio = 0.0 query = id + '=' + value num_match = re.findall('[0-9]+', value) if num_match == []: #数字ばかりのパラメータはマスタ番号の可能性が高いので除く for url in urls: if url.find(query) >= 0: id2url.setdefault(query, url) if num == 0: origin = url else: m = SM() m.set_seq1(origin) m.set_seq2(url) if m.ratio() > ratio: id2url[query] = url ratio = m.ratio() num += 1 #stateを分割するかを代表URLのDOM構造を見て決める i = 0 for id0, url0 in id2url.items(): j = 0 for id1, url1 in id2url.items(): if id0 != id1 and i >= j: similar = dif_html(url0, url1) if not similar: if not id0 in adopted: adopted.append(id0) if not id1 in adopted: adopted.append(id1) j += 1 i += 1 return adopted
def _merge(data, lower_criteria = 0.5, upper_criteria = 0.7, link_criteria = 0.4, img_criteria = 0.2, script_criteria = 0.2): for h0, s0 in data.items(): for state0, v0 in s0.items(): if data[h0][state0]['is_state']: for h1, s1 in data.items(): for state1, v1 in s1.items(): if data[h1][state1]['is_state']: if not (h0 == h1 and state0 == state1): similar = contents_features.dif_html(state0, state1, lower_criteria = lower_criteria, upper_criteria = upper_criteria, link_criteria = link_criteria, img_criteria = img_criteria, script_criteria = script_criteria) if similar: data[h1][state1]['is_state'] = False data[h1][state1]['merged_state'] = state0 return data