/* @brief Compare two bigints. * @param bia [in] A bigint. * @param bib [in] Another bigint. * @return -1 if smaller, 1 if larger and 0 if equal. */ internal int bi_compare(bigint bia, bigint bib) { if (bia.size > bib.size) { return(1); } if (bia.size < bib.size) { return(-1); } uint[] a = bia.comps; uint[] b = bib.comps; /* Same number of components. Compare starting from the high end * and working down. */ int i = bia.size - 1; do { if (a[i] > b[i]) { return(1); } if (a[i] < b[i]) { return(-1); } } while (--i >= 0); return(0); }
static bigint mul_bigint(bigint aa, bigint bb) { if (aa.bigint_len == 0) { return(aa); } else if (bb.bigint_len == 0) { return(bb); } else if (aa.bigint_len < 3 || bb.bigint_len < 3) { return(mul_bigint_cp(aa, bb)); } // Algorithme de Karatsuba int split = Math.Min(aa.bigint_len, bb.bigint_len) / 2; bigint a = bigint_shift(aa, -split); bigint b = bigint_premiers_chiffres(aa, split); bigint c = bigint_shift(bb, -split); bigint d = bigint_premiers_chiffres(bb, split); bigint amoinsb = sub_bigint(a, b); bigint cmoinsd = sub_bigint(c, d); bigint ac = mul_bigint(a, c); bigint bd = mul_bigint(b, d); bigint amoinsbcmoinsd = mul_bigint(amoinsb, cmoinsd); bigint acdec = bigint_shift(ac, 2 * split); return(add_bigint(add_bigint(acdec, bd), bigint_shift(sub_bigint(add_bigint(ac, bd), amoinsbcmoinsd), split))); // ac × 102k + (ac + bd – (a – b)(c – d)) × 10k + bd }
/* Make a new empty bigint. It may just use an old one if one is available. * Otherwise get one off the heap. */ private bigint Allocate(short size) { bigint result; /* Can we recycle an old bigint? */ if (null != this.free_list) { result = this.free_list; this.free_list = result.next; this.free_count--; if (0 != result.refs) { throw new InvalidOperationException(); } result.more_comps(size); } else { /* No free bigints available - create a new one. */ result = new bigint(); result.comps = new uint[size]; result.max_comps = size; /* give some space to spare */ } result.size = (short)size; result.refs = 1; result.next = null; this.active_count++; return(result); }
/* @brief Do a full copy of the bigint object. * @param ctx [in] The bigint session context. * @param bi [in] The bigint object to be copied. */ internal bigint bi_clone(bigint bi) { bigint result = this.Allocate(bi.size); Buffer.BlockCopy(bi.comps, 0, result.comps, 0, bi.size); return(result); }
/* @brief Perform an addition operation between two bigints. * @param ctx [in] The bigint session context. * @param bia [in] A bigint. * @param bib [in] Another bigint. * @return The result of the addition. */ internal bigint bi_add(bigint bia, bigint bib) { short n = Math.Max(bia.size, bib.size); bia.more_comps((short)(n + 1)); bib.more_comps(n); uint[] pa = bia.comps; uint[] pb = bib.comps; int aIndex = 0; int bIndex = 0; uint carry = 0; do { uint sl = pa[aIndex] + pb[bIndex++]; uint rl = sl + carry; carry = (uint)(((sl < pa[aIndex]) | (rl < sl)) ? 1 : 0); pa[aIndex++] = rl; } while (--n != 0); pa[aIndex] = carry; /* do overflow */ this.bi_free(bib); return(bia.trim()); }
/* @brief Convert an (unsigned) integer into a bigint. * @param ctx [in] The bigint session context. * @param i [in] The (unsigned) integer to be converted. */ internal bigint int_to_bi(uint i) { bigint biR = this.Allocate(1); biR.comps[0] = i; return(biR); }
static int euler29() { int maxA = 5; int maxB = 5; bigint[] a_bigint = new bigint[maxA + 1]; for (int j = 0; j <= maxA; j++) { a_bigint[j] = bigint_of_int(j * j); } bigint[] a0_bigint = new bigint[maxA + 1]; for (int j2 = 0; j2 <= maxA; j2++) { a0_bigint[j2] = bigint_of_int(j2); } int[] b = new int[maxA + 1]; for (int k = 0; k <= maxA; k++) { b[k] = 2; } int n = 0; bool found = true; while (found) { bigint min0 = a0_bigint[0]; found = false; for (int i = 2; i <= maxA; i++) { if (b[i] <= maxB) { if (found) { if (bigint_lt(a_bigint[i], min0)) { min0 = a_bigint[i]; } } else { min0 = a_bigint[i]; found = true; } } } if (found) { n++; for (int l = 2; l <= maxA; l++) { if (bigint_eq(a_bigint[l], min0) && b[l] <= maxB) { b[l]++; a_bigint[l] = mul_bigint(a_bigint[l], a0_bigint[l]); } } } } return(n); }
static bigint bigint_of_int(int i) { int size = log10(i); if (i == 0) { size = 0; } int[] t = new int[size]; for (int j = 0; j < size; j++) { t[j] = 0; } for (int k = 0; k < size; k++) { t[k] = i % 10; i /= 10; } bigint q = new bigint(); q.bigint_sign = true; q.bigint_len = size; q.bigint_chiffres = t; return(q); }
static bigint add_bigint_positif(bigint a, bigint b) { // Une addition ou on en a rien a faire des signes int len = Math.Max(a.bigint_len, b.bigint_len) + 1; int retenue = 0; int[] chiffres = new int[len]; for (int i = 0; i < len; i++) { int tmp = retenue; if (i < a.bigint_len) { tmp += a.bigint_chiffres[i]; } if (i < b.bigint_len) { tmp += b.bigint_chiffres[i]; } retenue = tmp / 10; chiffres[i] = tmp % 10; } while (len > 0 && chiffres[len - 1] == 0) { len--; } bigint f = new bigint(); f.bigint_sign = true; f.bigint_len = len; f.bigint_chiffres = chiffres; return(f); }
// http://projecteuler.net/problem=20 static int euler20() { bigint a = bigint_of_int(15); // normalement c'est 100 a = fact_bigint(a); return(sum_chiffres_bigint(a)); }
static int euler16() { bigint a = bigint_of_int(2); a = bigint_exp(a, 100); // 1000 normalement return(sum_chiffres_bigint(a)); }
static void Main() { bigint n1 = new bigint(5); bigint n2 = new bigint(2); bigint n3; n3 = n1 + n2; Console.WriteLine("Value of n3 = {0}", n3.val); }
/* @brief Take a permanent object and make it eligible for freedom. * @param bi [in] The bigint to be made back to temporary. */ internal void bi_depermanent(bigint bi) { if (bi.refs != PERMANENT) { throw new InvalidOperationException(); } bi.refs = 1; }
static bigint neg_bigint(bigint a) { bigint h = new bigint(); h.bigint_sign = !a.bigint_sign; h.bigint_len = a.bigint_len; h.bigint_chiffres = a.bigint_chiffres; return(h); }
public bigint SetMemory(bigint absAddress, bigint value) { if (absAddress > int.MaxValue) { throw new IndexOutOfRangeException("addresses need to bigint as well"); } var a = (int)absAddress; return(Memory[a] = value); }
/* @brief Pre-calculate some of the expensive steps in reduction. * This function should only be called once (normally when a session starts). * When the session is over, bi_free_mod() should be called. bi_mod_power() * relies on this function being called. * @param ctx [in] The bigint session context. * @param bim [in] The bigint modulus that will be used. * @param mod_offset [in] There are three moduluii that can be stored - the * standard modulus, and its two primes p and q. This offset refers to which * modulus we are referring to. * @see bi_free_mod(), bi_mod_power(). */ internal void bi_set_mod(bigint bim, int mod_offset) { int k = bim.size; uint d = (uint)((ulong)COMP_RADIX / ((ulong)bim.comps[k - 1] + 1)); this.bi_mod[mod_offset] = bim; this.bi_mod[mod_offset].bi_permanent(); this.bi_normalised_mod[mod_offset] = bi_int_multiply(bim, d); this.bi_normalised_mod[mod_offset].bi_permanent(); }
static int sum_chiffres_bigint(bigint a) { int out0 = 0; for (int i = 0; i < a.bigint_len; i++) { out0 += a.bigint_chiffres[i]; } return(out0); }
static void print_bigint(bigint a) { if (!a.bigint_sign) { Console.Write('-'); } for (int i = 0; i < a.bigint_len; i++) { Console.Write(a.bigint_chiffres[a.bigint_len - 1 - i]); } }
static bigint fact_bigint(bigint a) { bigint one = bigint_of_int(1); bigint out0 = one; while (!bigint_eq(a, one)) { out0 = mul_bigint(a, out0); a = sub_bigint(a, one); } return(out0); }
/* Perform an integer divide on a bigint. */ internal bigint bi_int_divide(bigint biR, uint denom) { int i = biR.size - 1; ulong r = 0; do { r = (r << COMP_BIT_SIZE) + biR.comps[i]; biR.comps[i] = (uint)(r / denom); r %= denom; } while (--i >= 0); return(biR.trim()); }
public bigint GetMemory(bigint absAddress) { if (absAddress > int.MaxValue) { throw new IndexOutOfRangeException("addresses need to bigint as well"); } var a = (int)absAddress; if (!Memory.TryGetValue(a, out bigint value)) { Memory[a] = 0; } return(Memory[a]); }
public int Amplifiers(int[] program, int[] phaseSettings) { bigint signal = 0; for (int i = 0; i < phaseSettings.Length; i++) { var p = new IntCodeComputer(program); p.Execute(new List <bigint> { phaseSettings[i], signal }); signal = p.Output.First(); } Console.WriteLine($"Phasesetting {string.Join(",", phaseSettings)} => {signal}"); return((int)signal); }
internal BigInteger mod_pow(BigInteger modulus, BigInteger exponent) { BI_CTX tmp_ctx = BI_CTX.bi_initialize(); tmp_ctx.bi_set_mod(tmp_ctx.bi_clone(modulus._impl), BIGINT_M_OFFSET); bigint tmp_biR = tmp_ctx.bi_mod_power(tmp_ctx.bi_clone(_impl), tmp_ctx.bi_clone(exponent._impl)); bigint biR = bigint_ctx.bi_clone(tmp_biR); tmp_ctx.bi_free(tmp_biR); tmp_ctx.bi_free_mod(BIGINT_M_OFFSET); tmp_ctx.bi_terminate(); return(new BigInteger(biR)); }
static bigint bigint_exp(bigint a, int b) { if (b == 1) { return(a); } else if (b % 2 == 0) { return(bigint_exp(mul_bigint(a, a), b / 2)); } else { return(mul_bigint(a, bigint_exp(a, b - 1))); } }
static bigint bigint_premiers_chiffres(bigint a, int i) { int len = Math.Min(i, a.bigint_len); while (len != 0 && a.bigint_chiffres[len - 1] == 0) { len--; } bigint o = new bigint(); o.bigint_sign = a.bigint_sign; o.bigint_len = len; o.bigint_chiffres = a.bigint_chiffres; return(o); }
/*@brief Clear the memory cache. */ internal void bi_clear_cache() { bigint pn; if (null == this.free_list) { return; } for (bigint p = this.free_list; null != p; p = pn) { pn = p.next; p.comps = null; } this.free_count = 0; this.free_list = null; }
static int euler25() { int i = 2; bigint a = bigint_of_int(1); bigint b = bigint_of_int(1); while (b.bigint_len < 100) { // 1000 normalement bigint c = add_bigint(a, b); a = b; b = c; i++; } return(i); }
static void euler48() { bigint sum = bigint_of_int(0); for (int i = 1; i < 101; i++) { // 1000 normalement bigint ib = bigint_of_int(i); bigint ibeib = bigint_exp_10chiffres(ib, i); sum = add_bigint(sum, ibeib); sum = bigint_premiers_chiffres(sum, 10); } Console.Write("euler 48 = "); print_bigint(sum); Console.Write("\n"); }
static bigint bigint_exp_10chiffres(bigint a, int b) { a = bigint_premiers_chiffres(a, 10); if (b == 1) { return(a); } else if (b % 2 == 0) { return(bigint_exp_10chiffres(mul_bigint(a, a), b / 2)); } else { return(mul_bigint(a, bigint_exp_10chiffres(a, b - 1))); } }
public static bigint operator +(bigint a, bigint b) { bigint c = new bigint(); c.size = Math.Max(a.size, b.size); for (int i = 1; i <= c.size; i++) c.a[i] = a.a[i] + b.a[i]; for (int i = 1; i <= c.size; i++) if (c.a[i] > 9) { c.a[i] -= 10; c.a[i + 1]++; if (i == c.size) c.size++; } return c; }
public static bigint operator -(bigint a, bigint b) { bigint c = new bigint(); c.size = Math.Max(a.size, b.size); for (int i = 1; i <= c.size; i++) c.a[i] = a.a[i] - b.a[i]; for (int i = 1; i <= c.size; i++) if (c.a[i] < 0) { c.a[i] += 10; c.a[i + 1]--; } while (c.a[c.size] == 0 && c.size > 1) c.size--; return c; }
private Replica( ReplicaId replicaId, bigint opsCounter, Node document, Map <Var, Cursor> variables, Set <Id> processedOps, Lst <Operation> generatedOps, Lst <Operation> receivedOps) { OpsCounter = opsCounter; Document = document; ReplicaId = replicaId; Variables = variables; ProcessedOps = processedOps; GeneratedOps = generatedOps; ReceivedOps = receivedOps; }
public static bigint operator *(bigint a, bigint b) { bigint c = new bigint(); c.size = a.size + b.size; for (int i = 1; i <= a.size; i++) for (int j = 1; j <= b.size; j++) c.a[i + j - 1] += a.a[i] * b.a[j]; for (int i = 1; i <= c.size; i++) if (c.a[i] > 9) { c.a[i + 1] += c.a[i] / 10; c.a[i] %= 10; if (i == c.size) c.size++; } while (c.a[c.size] == 0 && c.size > 1) c.size--; return c; }
private void equal_Click(object sender, EventArgs e) { bigint b = new bigint(); b.f(calctxt.Text); if (oper == 1) { last += b; calctxt.Text = last.ToString(); latest = b; loper = oper; } if (oper == 2) { last -= b; calctxt.Text = last.ToString(); latest = b; loper = oper; } if (oper == 3) { last *= b; calctxt.Text = last.ToString(); latest = b; loper = oper; } if (oper == 4) { if (loper == 1) { last += latest; calctxt.Text = last.ToString(); } if (loper == 2) { last -= latest; calctxt.Text = last.ToString(); } if(loper==3) { last *= latest; calctxt.Text = last.ToString(); } } oper = 4; }