예제 #1
0
/**
* @brief Perform a single source of the BC calculation per Brandes.
*
* Note that this follows the approach suggested by Green and Bader in which
* parent lists are not maintained, but instead the neighbors are searched
* to rediscover parents.
*
* Note also that found count will not include the source and that increments
* to this array are handled atomically.
*
* Operations to the bc array are NOT ATOMIC
*
* @param S The STINGER graph
* @param nv The maximum vertex ID in the graph plus one.
* @param source The vertex from where this search will start.
* @param bc The array into which the partial BCs will be added.
* @param found_count  An array to track how many times a vertex is found for normalization.
*/
void
single_bc_search(stinger_t * S, int64_t nv, int64_t source, double * bc, int64_t * found_count)
{
  int64_t * paths = (int64_t * )xcalloc(nv * 2, sizeof(int64_t));
  int64_t * q = paths + nv;
  double * partial = (double *)xcalloc(nv, sizeof(double));

  int64_t * d = (int64_t *)xmalloc(nv * sizeof(int64_t));
  for(int64_t i = 0; i < nv; i ++) d[i] = -1;

  int64_t q_front = 1;
  int64_t q_rear = 0;
  q[0] = source;
  d[source] = 0;
  paths[source] = 1;

  while(q_rear != q_front) {
    int64_t v = q[q_rear++];
    int64_t d_next = d[v] + 1;

    STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, v) {

      if(d[STINGER_EDGE_DEST] < 0) {
	d[STINGER_EDGE_DEST]     = d_next;
	paths[STINGER_EDGE_DEST] = paths[v];
	q[q_front++]             = STINGER_EDGE_DEST;

	stinger_int64_fetch_add(found_count + STINGER_EDGE_DEST, 1);
      }

      else if(d[STINGER_EDGE_DEST] == d_next) {
	paths[STINGER_EDGE_DEST] += paths[v];
      }

    } STINGER_FORALL_EDGES_OF_VTX_END();
  }

  /* don't process source */
  while(q_front > 1) {
    int64_t w = q[--q_front];

    /* don't maintain parents, do search instead */
    STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, w) {
      if(d[STINGER_EDGE_DEST] == (d[w] - 1)) {
	partial[STINGER_EDGE_DEST] += frac(paths[STINGER_EDGE_DEST],paths[w]) * (1 + partial[w]);
      }
    } STINGER_FORALL_EDGES_OF_VTX_END();
    bc[w] += partial[w];
  }

  free(d);
  free(partial);
  free(paths);
}
예제 #2
0
int64_t
//count_intersections (stinger_t * S, int64_t a, int64_t b)
count_intersections (stinger_t * S, int64_t a, int64_t b, int64_t * neighbors, int64_t d)
{
  size_t out = 0;
  
  STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, b) {

    if (STINGER_EDGE_DEST != a) {
      int64_t first = 0;
      int64_t last = d-1;
      int64_t middle = (first + last)/2;

      while (first <= last) {
	if (neighbors[middle] < STINGER_EDGE_DEST) {
	  first = middle + 1;
	} else if (neighbors[middle] == STINGER_EDGE_DEST) {
	  out++;
	  break;
	} else {
	  last = middle - 1;
	}

	middle = (first + last)/2;
      }
      //out += stinger_has_typed_successor (S, 0, STINGER_EDGE_DEST, a);
    }

  } STINGER_FORALL_EDGES_OF_VTX_END();


  return out;
}
예제 #3
0
static uint64_t
count_triangles(int_ht_seq_t * ht, stinger_t * S, int64_t v) {
  uint64_t count = 0;
  uint64_t count_check = 0;


  STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, v) {
    uint64_t neigh = STINGER_EDGE_DEST;

    STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, neigh) {
      if(STINGER_EDGE_DEST != v) {
	count += int_ht_seq_exists(ht, STINGER_EDGE_DEST);
      }
    } STINGER_FORALL_EDGES_OF_VTX_END();

    /*
    STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, neigh) {
      if(STINGER_EDGE_DEST != v) {
	uint64_t neigh_neigh = STINGER_EDGE_DEST;
	STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, v) {
	  count_check += (neigh_neigh == STINGER_EDGE_DEST);
	} STINGER_FORALL_EDGES_OF_VTX_END();
      }
    } STINGER_FORALL_EDGES_OF_VTX_END();
    */

    int_ht_seq_insert(ht, STINGER_EDGE_DEST);
  } STINGER_FORALL_EDGES_OF_VTX_END();
예제 #4
0
void betCentStinger_TraverseNeig_BFSqueue(struct stinger* sStinger,uint32_t currRoot,float* totalBC,bcTree* tree)
{

    for(uint32_t j = 0; j < tree->NV; j++)
    {
        tree->level[j] = INFINITY_MY;
        tree->pathsToRoot[j] = INFINITY_MY;
        tree->delta[j] = 0;

    }
	tree->level[currRoot] = 0;
	tree->pathsToRoot[currRoot] = 1;

    uint32_t Stack[tree->NV];
    uint32_t Queue[tree->NV];

    Queue[0] = currRoot;
    int32_t qStart=0,qEnd=1;
    int32_t sStart=0;

    // While queue is not empty
    while(qStart!=qEnd)
    {
        uint32_t currElement = Queue[qStart];
        Stack[sStart] = currElement;
        sStart++;
        qStart++;

        STINGER_FORALL_EDGES_OF_VTX_BEGIN(sStinger,currElement)
        {
            uint32_t k = STINGER_EDGE_DEST;

            // If this is a neighbor and has not been found
            if(tree->level[k] > tree->level[currElement])
            {
                // Checking if "k" has been found.
                if(tree->level[k]==INFINITY_MY)
                {
                    tree->level[k] = tree->level[currElement]+1;
                    Queue[qEnd++] = k;
                    tree->delta[k]=0;
                }

                if(tree->pathsToRoot[k] == INFINITY_MY)
                {
                    // k has not been found and therefore its paths to the roots are through its parent.
                    tree->pathsToRoot[k] = tree->pathsToRoot[currElement];

                }
                else
                {
                    // k has been found and has multiple paths to the root as it has multiple parents.
                    tree->pathsToRoot[k] += tree->pathsToRoot[currElement];
                }
            }
        }
        STINGER_FORALL_EDGES_OF_VTX_END();
    }
예제 #5
0
int64_t
pagerank (stinger_t * S, int64_t NV, double * pr, double * tmp_pr_in, double epsilon, double dampingfactor, int64_t maxiter)
{
  double * tmp_pr = NULL;
  if(tmp_pr_in) {
    tmp_pr = tmp_pr_in;
  } else {
    tmp_pr = (double *) xmalloc (sizeof(double) * NV);
  }

  int64_t iter = maxiter;
  double delta = 1;

  while (delta > epsilon && iter > 0) {
    OMP("omp parallel for")
    for (uint64_t v = 0; v < NV; v++) {
      tmp_pr[v] = 0;

      STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, v) {
	tmp_pr[v] += (((double)pr[STINGER_EDGE_DEST]) / 
	  ((double) stinger_outdegree_get(S, STINGER_EDGE_DEST)));
      } STINGER_FORALL_EDGES_OF_VTX_END();
    }

    OMP("omp parallel for")
    for (uint64_t v = 0; v < NV; v++) {
      tmp_pr[v] = tmp_pr[v] * dampingfactor + (((double)(1-dampingfactor)) / ((double)NV));
    }

    delta = 0;
    OMP("omp parallel for reduction(+:delta)")
    for (uint64_t v = 0; v < NV; v++) {
      double mydelta = tmp_pr[v] - pr[v];
      if(mydelta < 0)
	mydelta = -mydelta;
      delta += mydelta;
    }

    OMP("omp parallel for")
    for (uint64_t v = 0; v < NV; v++) {
      pr[v] = tmp_pr[v];
    }
  }

  if (!tmp_pr_in)
    free(tmp_pr);
}
예제 #6
0
파일: main.c 프로젝트: anukat2015/DynoGraph
int64_t
parallel_breadth_first_search (struct stinger * S, int64_t nv,
				      int64_t source, int64_t * marks,
                                      int64_t * queue, int64_t * Qhead, int64_t * level)
{
  for (int64_t i = 0; i < nv; i++) {
    level[i] = -1;
    marks[i] = 0;
  }
  
  int64_t nQ, Qnext, Qstart, Qend;
  /* initialize */
  queue[0] = source;
  level[source] = 0;
  marks[source] = 1;
  Qnext = 1;  /* next open slot in the queue */
  nQ = 1;     /* level we are currently processing */
  Qhead[0] = 0;  /* beginning of the current frontier */
  Qhead[1] = 1;  /* end of the current frontier */
 
  Qstart = Qhead[nQ-1];
  Qend = Qhead[nQ];

  while (Qstart != Qend) {
    OMP ("omp parallel for")
    for (int64_t j = Qstart; j < Qend; j++) {
      STINGER_FORALL_EDGES_OF_VTX_BEGIN (S, queue[j]) {
	int64_t d = level[STINGER_EDGE_DEST];
	if (d < 0) {
	  if (stinger_int64_fetch_add (&marks[STINGER_EDGE_DEST], 1) == 0) {
	    level[STINGER_EDGE_DEST] = nQ;

	    int64_t mine = stinger_int64_fetch_add(&Qnext, 1);
	    queue[mine] = STINGER_EDGE_DEST;
	  }
	}
      } STINGER_FORALL_EDGES_OF_VTX_END();
    }
    
    Qstart = Qhead[nQ-1];
    Qend = Qnext;
    Qhead[nQ++] = Qend;
  }
예제 #7
0
// NE number of undirected edges.
csrGraph* CreateCSRFromStinger(struct stinger* stingerGraph,int64_t NV,int64_t NE)
{
    csrGraph* newGraph = (csrGraph*)malloc(sizeof(csrGraph));
    newGraph->NV = NV;
    newGraph->NE = NE*2;

    newGraph->vertexPointerArray=(int64_t*)malloc(sizeof(int64_t)*(NV+1));
    newGraph->edgeArray=(int64_t*)malloc(sizeof(int64_t)*NE);

    int64_t edgeCounter=0;
    newGraph->vertexPointerArray[0]=0;
    for(int64_t v=0; v<NV;v++)
    {
        newGraph->vertexPointerArray[v+1]= newGraph->vertexPointerArray[v]+stinger_outdegree(stingerGraph,v);

        STINGER_FORALL_EDGES_OF_VTX_BEGIN(stingerGraph,v)
        {
            newGraph->edgeArray[edgeCounter]=STINGER_EDGE_DEST;
            edgeCounter++;
        }
        STINGER_FORALL_EDGES_OF_VTX_END();
    }
예제 #8
0
int64_t
count_triangles (stinger_t * S, uint64_t v)
{
  int64_t out = 0;

  int64_t deg = stinger_outdegree(S, v);
  int64_t * neighbors = xmalloc(deg * sizeof(int64_t));
  size_t d;
  stinger_gather_typed_successors(S, 0, v, &d, neighbors, deg);
  qsort(neighbors, d, sizeof(int64_t), compare);

  STINGER_FORALL_EDGES_OF_VTX_BEGIN(S, v) {

    if (STINGER_EDGE_DEST != v) {
      //out += count_intersections (S, v, STINGER_EDGE_DEST);
      out += count_intersections (S, v, STINGER_EDGE_DEST, neighbors, d);
    }

  } STINGER_FORALL_EDGES_OF_VTX_END();

  free (neighbors);

  return out;
}