コード例 #1
0
ファイル: list1.c プロジェクト: riya305/ADT
/* A program to test above function*/
     int main()
    {
    /* Start with the empty list */
    lnodeptr head1 = NULL;
    lnodeptr head2 = NULL;
    
 
    /*create a linked lists 4->3->2->1 */
    list_push(&head1, 1);
    list_push(&head1, 2);
    list_push(&head1, 3);
    list_push(&head1, 4);
 
    /*create a linked lists 7->6->5->4 */
    list_push(&head2, 4);
    list_push(&head2, 5);
    list_push(&head2, 6);
    list_push(&head2, 7);
    
    
   /*create a linked lists 4->3->2->1->7->6->5->4 */ 
    list_add(&head2,head1);

    list_pop(&head1);
    list_pop(&head1);
    list_pop(&head1);
    list_pop(&head1);
    list_pop(&head1);
    list_pop(&head1);

    

    list_push(&head2, 8);
    list_push(&head2, 9);
    list_push(&head2, 10);
    list_push(&head2, 11);
    

    

    list_sub(&head1,head2);
    
    

    list_pop(&head1);
    list_pop(&head1);
    list_pop(&head1);
    printf("\n%d",list_length(head2));
    printf("\n%d",list_length(head1));



    return 0;
   }
コード例 #2
0
ファイル: listz.c プロジェクト: CplusHua/yafu-setup-package
/*
  Returns in a[0]+a[1]*x+...+a[K-1]*x^(K-1)
  the remainder of the division of
  A = a[0]+a[1]*x+...+a[2K-2]*x^(2K-2)
  by B = b[0]+b[1]*x+...+b[K-1]*x^(K-1)+b[K]*x^K with b[K]=1 *explicit*.
  (We have A = Q*B + R with deg(Q)=K-2 and deg(R)=K-1.)
  Assumes invb[0]+invb[1]*x+...+invb[K-2]*x^(K-2) equals Quo(x^(2K-2), B).
  Assumes K >= 2.
  Requires 2K-1 + list_mul_mem(K) cells in t.

  Notations: R = r[0..K-1], A = a[0..2K-2], low(A) = a[0..K-1],
  high(A) = a[K..2K-2], Q = t[0..K-2]
  Return non-zero iff an error occurred.
*/
int
PrerevertDivision (listz_t a, listz_t b, listz_t invb,
                   unsigned int K, listz_t t, mpz_t n)
{
  int po2, wrap;
  listz_t t2 = NULL;
#ifdef WRAP
  wrap = ks_wrapmul_m (K + 1, K + 1, n) <= 2 * K - 1 + list_mul_mem (K);
#else
  wrap = 0;
#endif

  /* Q <- high(high(A) * INVB) with a short product */
  for (po2 = K; (po2 & 1) == 0; po2 >>= 1);
  po2 = (po2 == 1);
  if (Fermat && po2)
    {
      mpz_set_ui (a[2 * K - 1], 0);
      if (K <= 4 * Fermat)
        {
          F_mul (t, a + K, invb, K, DEFAULT, Fermat, t + 2 * K);
          /* Put Q in T, as we still need high(A) later on */
          list_mod (t, t + K - 2, K, n);
        }
      else
        {
          F_mul (t, a + K, invb, K, DEFAULT, Fermat, t + 2 * K);
          list_mod (a + K, t + K - 2, K, n);
        }
    }
  else /* non-Fermat case */
    {
      list_mul_high (t, a + K, invb, K - 1, t + 2 * K - 3);
      /* the high part of A * INVB is now in {t+K-2, K-1} */
      if (wrap)
	{
	  MEMORY_TAG;
	  t2 = init_list2 (K - 1, mpz_sizeinbase (n, 2));
	  MEMORY_UNTAG;
	  if (t2 == NULL)
	    {
	      fprintf (ECM_STDERR, "Error, not enough memory\n");
	      return ECM_ERROR;
	    }
	  list_mod (t2, t + K - 2, K - 1, n);
	}
      else /* we can store in high(A) which is no longer needed */
	list_mod (a + K, t + K - 2, K - 1, n);
    }

  /* the quotient Q = trunc(A / B) has degree K-2, i.e. K-1 terms */

  /* T <- low(Q * B) with a short product */
  mpz_set_ui (a[2 * K - 1], 0);
  if (Fermat && po2)
    {
      if (K <= 4 * Fermat)
        {
          /* Multiply without zero padding, result is (mod x^K - 1) */
          F_mul (t + K, t, b, K, NOPAD, Fermat, t + 2 * K);
          /* Take the leading monomial x^K of B into account */
          list_add (t, t + K, t, K);
          /* Subtract high(A) */
          list_sub(t, t, a + K, K);
        }
      else
        F_mul (t, a + K, b, K, DEFAULT, Fermat, t + 2 * K);
    }
  else /* non-Fermat case */
    {
#ifdef KS_MULTIPLY /* ks is faster */
      if (wrap)
        /* Q = {t2, K-1}, B = {b, K+1}
           We know that Q*B vanishes with the coefficients of degree
           K to 2K-2 of {A, 2K-1} */
        {
          unsigned int m;
          m = ks_wrapmul (t, K + 1, b, K + 1, t2, K - 1, n);
          clear_list (t2, K - 1);
          /* coefficients of degree m..2K-2 wrap around,
             i.e. were subtracted to 0..2K-2-m */
          if (m < 2 * K - 1) /* otherwise product is exact */
            list_add (t, t, a + m, 2 * K - 1 - m);
        }
      else
        LIST_MULT_N (t, a + K, b, K, t + 2 * K - 1);
#else
      list_mul_low (t, a + K, b, K, t + 2 * K - 1, n);
#endif
    }

  /* now {t, K} contains the low K terms from Q*B */
  list_sub (a, a, t, K);
  list_mod (a, a, K, n);

  return 0;
}
コード例 #3
0
ファイル: listz.c プロジェクト: CplusHua/yafu-setup-package
/*
  divides a[0]+a[1]*x+...+a[2K-1]*x^(2K-1)
  By b[0]+b[1]*x+...+b[K-1]*x^(K-1)+x^K
  i.e. a polynomial of 2K coefficients divided by a monic polynomial
  with K+1 coefficients (b[K]=1 is implicit).
  Puts the quotient in q[0]+q[1]*x+...+q[K-1]*x^(K-1)
  and the remainder in a[0]+a[1]*x+...+a[K-1]*x^(K-1)
  Needs space for list_mul_mem(K) coefficients in t.
  If top is non-zero, a[0]..a[K-1] are reduced mod n.
*/
void
RecursiveDivision (listz_t q, listz_t a, listz_t b, unsigned int K,
                   listz_t t, mpz_t n, int top)
{
  if (K == 1) /* a0+a1*x = a1*(b0+x) + a0-a1*b0 */
    {
      mpz_mod (a[1], a[1], n);
      mpz_mul (q[0], a[1], b[0]);
      mpz_mod (q[0], q[0], n);
      mpz_sub (a[0], a[0], q[0]);
      if (top)
        mpz_mod (a[0], a[0], n);
      mpz_set (q[0], a[1]);
    }
  else
    {
      unsigned int k, l, i, po2;

      k = K / 2;
      l = K - k;
      for (po2 = K; (po2 && 1) == 0; po2 >>= 1);
      po2 = (po2 == 1);

      /* first perform a (2l) / l division */
      RecursiveDivision (q + k, a + 2 * k, b + k, l, t, n, 0);
      /* subtract q[k..k+l-1] * b[0..k-1] */
      ASSERTD(list_check(q+l,k,n) && list_check(b,k,n));
      if (po2 && Fermat)
        F_mul (t, q + l, b, k, DEFAULT, Fermat, t + K); /* sets t[0..2*k-2]*/
      else
        LIST_MULT_N (t, q + l, b, k, t + K - 1); /* sets t[0..2*k-2] */
      list_sub (a + l, a + l, t, 2 * k - 1);
      if (k < l) /* don't forget to subtract q[k] * b[0..k-1] */
        {
	  for (i=0; i<k; i++)
	    {
	      mpz_mul (t[0], q[k], b[i]); /* TODO: need to reduce t[0]? */
	      mpz_sub (a[k+i], a[k+i], t[0]);
	    }
        }
      /* remainder is in a[0..K+k-1] */

      /* then perform a (2k) / k division */
      RecursiveDivision (q, a + l, b + l, k, t, n, 0);
      /* subtract q[0..k-1] * b[0..l-1] */
      ASSERTD(list_check(q,k,n) && list_check(b,k,n));
      if (po2 && Fermat)
        F_mul (t, q, b, k, DEFAULT, Fermat, t + K);
      else
        LIST_MULT_N (t, q, b, k, t + K - 1);
      list_sub (a, a, t, 2 * k - 1);
      if (k < l) /* don't forget to subtract q[0..k-1] * b[k] */
        {
          for (i=0; i<k; i++)
            {
              mpz_mul (t[0], q[i], b[k]); /* TODO: need to reduce t[0]? */
              mpz_sub (a[k+i], a[k+i], t[0]);
            }
        }

      /* normalizes the remainder wrt n */
      if (top)
        list_mod (a, a, K, n);
    }
}
コード例 #4
0
ファイル: listz.c プロジェクト: CplusHua/yafu-setup-package
/* puts in q[0..K-1] the quotient of x^(2K-2) by B
   where B = b[0]+b[1]*x+...+b[K-1]*x^(K-1) with b[K-1]=1.
*/
void
PolyInvert (listz_t q, listz_t b, unsigned int K, listz_t t, mpz_t n)
{
  if (K == 1)
    {
      mpz_set_ui (q[0], 1);
      return;
    }
  else
    {
      int k, l, po2, use_middle_product = 0;

#ifdef KS_MULTIPLY
      use_middle_product = 1;
#endif

      k = K / 2;
      l = K - k;

      for (po2 = K; (po2 & 1) == 0; po2 >>= 1);
      po2 = (po2 == 1 && Fermat != 0);

      /* first determine l most-significant coeffs of Q */
      PolyInvert (q + k, b + k, l, t, n); /* Q1 = {q+k, l} */

      /* now Q1 * B = x^(2K-2) + O(x^(2K-2-l)) = x^(2K-2) + O(x^(K+k-2)).
         We need the coefficients of degree K-1 to K+k-2 of Q1*B */

      ASSERTD(list_check(q+k,l,n) && list_check(b,l,n));
      if (po2 == 0 && use_middle_product)
        {
          TMulKS (t, k - 1, q + k, l - 1, b, K - 1, n, 0);
          list_neg (t, t, k, n);
        }
      else if (po2)
        {
          list_revert (q + k, l);
          /* This expects the leading monomials explicitly in q[2k-1] and b[k+l-1] */
          F_mul_trans (t, q + k, b, K / 2, K, Fermat, t + k);
          list_revert (q + k, l);
          list_neg (t, t, k, n);
        }
      else
        {
          LIST_MULT_N (t, q + k, b, l, t + 2 * l - 1); /* t[0..2l-1] = Q1 * B0 */
          list_neg (t, t + l - 1, k, n);
      
          if (k > 1)
            {
              list_mul (t + k, q + k, l - 1, 1, b + l, k - 1, 1,
			t + k + K - 2); /* Q1 * B1 */
              list_sub (t + 1, t + 1, t + k, k - 1);
            }
        }
      list_mod (t, t, k, n); /* high(1-B*Q1) */

      ASSERTD(list_check(t,k,n) && list_check(q+l,k,n));
      if (po2)
        F_mul (t + k, t, q + l, k, DEFAULT, Fermat, t + 3 * k);
      else
        LIST_MULT_N (t + k, t, q + l, k, t + 3 * k - 1);
      list_mod (q, t + 2 * k - 1, k, n);
    }
}
コード例 #5
0
ファイル: listz.c プロジェクト: CplusHua/yafu-setup-package
/* Puts in a[0..2K-2] the product of b[0..K-1] and c[0..K-1].
   The auxiliary memory M(K) necessary in T satisfies:
   M(1)=0, M(K) = max(3*l-1,2*l-2+M(l)) <= 2*K-1 where l = ceil(K/2).
   Assumes K >= 1.
*/
void
karatsuba (listz_t a, listz_t b, listz_t c, unsigned int K, listz_t t)
{
  if (K == 1)
    {
      mpz_mul (a[0], b[0], c[0]);
    }
  else if (K == 2) /* basic Karatsuba scheme */
    {
      mpz_add (t[0], b[0], b[1]); /* t0 = b_0 + b_1 */
      mpz_add (a[1], c[0], c[1]); /* a1 = c_0 + c_1 */
      mpz_mul (a[1], a[1], t[0]); /* a1 = b_0*c_0 + b_0*c_1 + b_1*c_0 + b_1*c_1 */
      mpz_mul (a[0], b[0], c[0]); /* a0 = b_0 * c_0 */
      mpz_mul (a[2], b[1], c[1]); /* a2 = b_1 * c_1 */
      mpz_sub (a[1], a[1], a[0]); /* a1 = b_0*c_1 + b_1*c_0 + b_1*c_1 */
      mpz_sub (a[1], a[1], a[2]); /* a1 = b_0*c_1 + b_1*c_0 */
    }
  else if (K == 3)
    {
      /* implement Weimerskirch/Paar trick in 6 muls and 13 adds
         http://www.crypto.ruhr-uni-bochum.de/Publikationen/texte/kaweb.pdf */
      /* diagonal terms */
      mpz_mul (a[0], b[0], c[0]);
      mpz_mul (a[2], b[1], c[1]);
      mpz_mul (a[4], b[2], c[2]);
      /* (0,1) rectangular term */
      mpz_add (t[0], b[0], b[1]);
      mpz_add (t[1], c[0], c[1]);
      mpz_mul (a[1], t[0], t[1]);
      mpz_sub (a[1], a[1], a[0]);
      mpz_sub (a[1], a[1], a[2]);
      /* (1,2) rectangular term */
      mpz_add (t[0], b[1], b[2]);
      mpz_add (t[1], c[1], c[2]);
      mpz_mul (a[3], t[0], t[1]);
      mpz_sub (a[3], a[3], a[2]);
      mpz_sub (a[3], a[3], a[4]);
      /* (0,2) rectangular term */
      mpz_add (t[0], b[0], b[2]);
      mpz_add (t[1], c[0], c[2]);
      mpz_mul (t[2], t[0], t[1]);
      mpz_sub (t[2], t[2], a[0]);
      mpz_sub (t[2], t[2], a[4]);
      mpz_add (a[2], a[2], t[2]);
    }
  else
    { 
      unsigned int i, k, l;
      listz_t z;

      k = K / 2;
      l = K - k;

      z = t + 2 * l - 1;

      /* improved code with 7*k-3 additions, 
         contributed by Philip McLaughlin <*****@*****.**> */
      for (i = 0; i < k; i++)
        {
          mpz_sub (z[i], b[i], b[l+i]);
          mpz_sub (a[i], c[i], c[l+i]);
        }

      if (l > k) /* case K odd */
        {
          mpz_set (z[k], b[k]);
          mpz_set (a[k], c[k]);
        }

      /* as b[0..l-1] + b[l..K-1] is stored in t[2l-1..3l-2], we need
         here at least 3l-1 entries in t */

      karatsuba (t, z, a, l, a + l); /* fills t[0..2l-2] */
       
      /* trick: save t[2l-2] in a[2l-1] to enable M(K) <= 2*K-1 */
      z = t + 2 * l - 2;
      mpz_set (a[2*l-1], t[2*l-2]);

      karatsuba (a, b, c, l, z); /* fill a[0..2l-2] */
      karatsuba (a + 2 * l, b + l, c + l, k, z); /* fills a[2l..2K-2] */

      mpz_set (t[2*l-2], a[2*l-1]); /* restore t[2*l-2] */
      mpz_set_ui (a[2*l-1], 0);

      /*
	      l          l-1     1    l          2k-1-l
        _________________________________________________
	|    a0    |     a1    |0|    a2    |     a3    |
        -------------------------------------------------
              l          l-1
        ________________________
	|    t0    |     t1    |
        ------------------------

	We want to replace [a1, a2] by [a1 + a0 + a2 - t0, a2 + a1 + a3 - t1]
	i.e. [a12 + a0 - t0, a12 + a3 - t1] where a12 = a1 + a2.
       */

      list_add (a + 2 * l, a + 2 * l, a + l, l-1); /* a[2l..3l-1] <- a1+a2 */
      if (k > 1)
        {
          list_add (a + l, a + 2 * l, a, l); /* a[l..2l-1] <- a0 + a1 + a2 */
          list_add (a + 2 * l, a + 2 * l, a + 3 * l, 2 * k - 1 - l);
        }
      else /* k=1, i.e. K=2 or K=3, and a2 has only one entry */
        {
          mpz_add (a[l], a[2*l], a[0]);
          if (K == 3)
            mpz_set (a[l+1], a[1]);
        }

      list_sub (a + l, a + l, t, 2 * l - 1);
    }
}
コード例 #6
0
ファイル: lists.c プロジェクト: SKAcz/bics-current
/* add or subtract something to/from a list */
int list_addsub(int p, char* list, char* who, int addsub)
{
  struct player *pp = &player_globals.parray[p];
  int p1, connected, loadme, personal, ch;
  char *listname, *member, junkChar;
  struct List *gl;
  char *yourthe, *addrem;

  gl = list_findpartial(p, list, addsub);
  if (!gl)
    return COM_OK;

  personal = ListArray[gl->which].rights == P_PERSONAL;
  loadme = (gl->which != L_FILTER) && (gl->which != L_REMOVEDCOM) && (gl->which != L_CHANNEL);
  listname = ListArray[gl->which].name;
  yourthe = personal ? "your" : "the";
  addrem = (addsub == 1) ? "added to" : "removed from";

  if (loadme) {
    if (!FindPlayer(p, who, &p1, &connected)) {
      if (addsub == 1)
        return COM_OK;
      member = who;		/* allow sub removed/renamed player */
      loadme = 0;
    } else
      member = player_globals.parray[p1].name;
  } else {
    member = who;
  }

  if (addsub == 1) {		/* add to list */

   if (gl->which == L_CHANNEL) {

     if (sscanf (who,"%d%c",&ch, &junkChar) == 1 && ch >= 0 && ch < 255) {
       if ((ch == 0) && (!in_list(p,L_ADMIN,pp->name))) {
         pprintf(p, "Only admins may join channel 0.\n");
         return COM_OK;
       }
     } else {
         pprintf (p,"The channel to add must be a number between 0 and %d.\n",MAX_CHANNELS - 1);
         return COM_OK;
  	}
  }
  if (in_list(p, gl->which, member)) {
     pprintf(p, "[%s] is already on %s %s list.\n", member, yourthe, listname);
     if (loadme && !connected)
       player_remove(p1);
     return COM_OK;
    }
    if (list_add(p, gl->which, member)) {
      pprintf(p, "Sorry, %s %s list is full.\n", yourthe, listname);
      if (loadme && !connected)
	player_remove(p1);
      return COM_OK;
    }
  } else if (addsub == 2) {	/* subtract from list */
    if (!in_list(p, gl->which, member)) {
      pprintf(p, "[%s] is not in %s %s list.\n", member, yourthe, listname);
      if (loadme && !connected)
	player_remove(p1);
      return COM_OK;
    }
    list_sub(p, gl->which, member);
  }
  pprintf(p, "[%s] %s %s %s list.\n", member, addrem, yourthe, listname);

  if (!personal) {
    FILE *fp;
    char filename[MAX_FILENAME_SIZE];

    switch (gl->which) {
    case L_MUZZLE:
    case L_CMUZZLE:
    case L_C1MUZZLE:
    case L_C24MUZZLE:
    case L_C46MUZZLE:
    case L_C49MUZZLE:
    case L_C50MUZZLE:
    case L_C51MUZZLE:
    case L_ABUSER:
    case L_BAN:
    case L_NOTEBAN:
    case L_RATEBAN:
      pprintf(p, "Please leave a comment to explain why %s was %s the %s list.\n", member, addrem, listname);
      pcommand(p, "addcomment %s %s %s list.\n", member, addrem, listname);
      break;
    case L_COMPUTER:
      /*if (player_globals.parray[p1].z_stats.rating > 0)
	UpdateRank(TYPE_CRAZYHOUSE, member, &player_globals.parray[p1].z_stats, member);
      if (player_globals.parray[p1].s_stats.rating > 0)
	UpdateRank(TYPE_STAND, member, &player_globals.parray[p1].s_stats, member);
      if (player_globals.parray[p1].w_stats.rating > 0)
	UpdateRank(TYPE_WILD, member, &player_globals.parray[p1].w_stats, member);*/
      break;
    case L_ADMIN:
      if (addsub == 1) {	/* adding to list */
	player_globals.parray[p1].adminLevel = 10;
	pprintf(p, "%s has been given an admin level of 10 - change with asetadmin.\n", member);
      } else {
	player_globals.parray[p1].adminLevel = 0;
      }
      break;
    case L_FILTER:
    case L_REMOVEDCOM:
    default:
      break;
    }

    if (loadme && connected)
        pprintf_prompt(p1, "You have been %s the %s list by %s.\n",
                                    addrem, listname, pp->name);

    sprintf(filename, "%s/%s", LISTS_DIR, listname);
    fp = fopen_s(filename, "w");
    if (fp == NULL) {
      d_printf( "Couldn't save %s list.\n", listname);
    } else {
      int i;
      for (i = 0; i < gl->numMembers; i++)
	fprintf(fp, "%s\n", gl->m_member[i]);
      fclose(fp);
    }
  }
  if (loadme || (gl->which == L_ADMIN)) {
    player_save(p1);
  }
  if (loadme && !connected) {
    player_remove(p1);
  }
  return COM_OK;
}