Principe du PageRank et implémentation du langage C

PageRank est un algorithme de classement des moteurs de recherche développé par le cofondateur de Google, Larry Page. L'algorithme considère Internet comme un graphe orienté, où les pages Web sont représentées sous forme de nœuds et les liens (hyperliens) sont représentés sous forme de bords.

Le principe de base du PageRank est de donner à chaque page un "poids", qui dépend de l'évaluation complète du nombre et de la qualité de la page Web connectée par d'autres pages Web. Plus précisément, lorsqu'il existe de nombreuses pages pointant vers la même page, cette page sera considérée comme plus importante (plus populaire) et obtiendra ainsi un poids plus élevé.

Lors du calcul de la valeur PageRank, chaque page se verra attribuer une valeur initiale (généralement 1). Ensuite, la valeur PageRank de chaque page est calculée plusieurs fois à l'aide d'un algorithme itératif jusqu'à convergence.

Lors du calcul, la valeur PageRank de chaque nœud sera collectée à partir de tous les nœuds entrants qui lui sont associés (c'est-à-dire les nœuds pointant vers ce nœud), et les valeurs PageRank de ces nœuds entrants seront divisées selon le rapport égal de ses bords adjacents Calcul. En fin de compte, la valeur PageRank est considérée comme le poids relatif de chaque nœud pour les classements des moteurs de recherche.

En bref, l'algorithme PageRank détermine principalement l'importance relative de la page en évaluant la quantité et la qualité des liens entrants de la page Web, et vers quelles pages ces liens pointent, et effectue le classement des moteurs de recherche en conséquence.

Sa formule de mise en œuvre est la suivante :

  Pour pour F ou   t = 0 : \ t = 0 : t=0:
PR ( pi ; t ) = 1 NPR\left(p_{i} ; t\right)=\frac{1}{N}RP( pje;t )=N1
  Pour pour F ou   t > 0 : \ t > 0 : t>0:

PR ( pj ; t ) = 1 - ré N + ré × ( ( ∑ pj ∈ M ( pi ) PR ( pj ; t - 1 ) ré ( pj ) ) + ( ∑ pj ∈ SPR ( pj ; t - 1 ) N ) ) PR\left(p_{j} ; t\right)=\frac{1-d}{N}+d \times\left(\left(\sum_{p _{j} \in M\left( p_{i}\right)} \frac{PR\left(p_{j} ; t-1\right)}{D\left(p_{j}\right)}\right)+\left(\sum_{ p_{j} \in S} \frac{PR\left(p_{j} ; t-1\right)}{N}\right)\right)RP( pje;t )=N1+d× pjeM ( pje)D( pje)RP( pje;t1 ) + pjeSNRP( pje;t1 )

L'implémentation en langage C de l'algorithme est la suivante :

  • Définition de la structure :
//边表结点
typedef struct ArcNode{
    
    
	int adjvex;		//某条边指向的那个顶点的位置
	ArcNode * next;	//指向下一条弧的指针 
	weight w;		//权值
}ArcNode; 
//顶点表结点
typedef struct VNode{
    
    
	VertexType data;	//顶点信息
	double oldrank;
	double pagerank;
//	double sink_rank;
	ArcNode * first;	//指向第一条依附该顶点的弧的指针
}VNode;
typedef struct GraphRepr{
    
    
	VNode * node;		//邻接表
	int vexnum, arcnum;	//图的顶点数和弧数 
}Graph, *graph; 
  • Implémentation de l'algorithme :
void graph_pagerank(graph g, double damping, double delta) {
    
    
	double sink_rank = 0;
    int N = graph_vertices_count(g);
    for(int i = 0; i < N; i++){
    
    
    	g->node[i].oldrank = 0;
		g->node[i].pagerank = 1.0/N;    
//		printf("%lf\n", g->node[i].pagerank);	
	}
	double temp_delta, min_delta = INF;
	for(int i = 0; i < N; i++){
    
    
		temp_delta = g->node[i].pagerank - g->node[i].oldrank > 0 ? g->node[i].pagerank - g->node[i].oldrank : g->node[i].oldrank - g->node[i].pagerank;
		if(temp_delta < min_delta) min_delta = temp_delta;
	}
	while(temp_delta > delta){
    
    
//		printf("%lf\n", temp_delta);
		for(int j = 0; j < N; j++){
    
    
			g->node[j].oldrank = g->node[j].pagerank;
//			printf("%lf ", g->node[j].pagerank);
		}
//		putchar('\n');
		sink_rank = 0;
		for(int j = 0; j < N; j++){
    
    
			if(g->node[j].first == NULL){
    
    
				sink_rank = sink_rank + (damping * (g->node[j].oldrank / (double)N));
			}
		}
		for(int j = 0; j < N; j++){
    
    
			g->node[j].pagerank = sink_rank + ((1 - damping) / (double)N);
			for(int k = 0; k < N; k++){
    
    
				ArcNode * temp = g->node[k].first;
				while(temp){
    
    
					if(temp->adjvex == j){
    
    
//						printf("%d\n", temp->adjvex);
						int num_outbound_edge = 1;
						ArcNode * temp_num = g->node[k].first;
						while(temp_num->next){
    
    
							num_outbound_edge++;
							temp_num = temp_num->next;
						}
//						printf("%d\n", num_outbound_edge);
						g->node[j].pagerank = g->node[j].pagerank + ((damping * g->node[k].oldrank) / (double)num_outbound_edge);
						break;
					}
					temp = temp->next;
				}
			}
		}
		min_delta = INF;
		for(int i = 0; i < N; i++){
    
    
			temp_delta = g->node[i].pagerank - g->node[i].oldrank > 0 ? g->node[i].pagerank - g->node[i].oldrank : g->node[i].oldrank - g->node[i].pagerank;
			if(temp_delta < min_delta) min_delta = temp_delta;
		}
	}		
		
    return;
}

Je suppose que tu aimes

Origine blog.csdn.net/z135733/article/details/130499905
conseillé
Classement