Пример #1
0
int main()
{
	char num1[100];
	char num2[100];
	char op[2];
	while(scanf("%s",num1) != EOF)
	{
		getchar();
		scanf("%s", op);
		scanf("%s", num2);
		reverseStr(num1);
		reverseStr(num2);

		char ret[100] = {0};
			if(op[0] == '*')
			{
				bigMulChar(num1, num2, ret);
			}
			else
			{
				bigDivide(num1, num2, ret);
			}
			reverseStr(ret);
			printf("%s\n", ret);
	}
	return 0;
}
Пример #2
0
void getRet(char* ret, int n, int m)
{
    int i;

    for(i = m + n; i > 1; i--)
    {
        bigMuti(ret, i);
    }
    bigMuti(ret, m + 1 - n);
    bigDivide(ret, m + 1);
}
Пример #3
0
void getRet(char* ret, int n)
{
    int i;

    for(i = 2 * n; i > n; i--)
    {
        bigMuti(ret, i);
    }
    for(i = 2; i <= n + 1; i++)
    {
        bigDivide(ret, i);
    }
}
Пример #4
0
bool
InflationOpFrame::doApply(medida::MetricsRegistry& metrics, LedgerDelta& delta,
                          LedgerManager& ledgerManager)
{
    LedgerDelta inflationDelta(delta);

    auto& lcl = inflationDelta.getHeader();

    time_t closeTime = lcl.scpValue.closeTime;
    uint32_t seq = lcl.inflationSeq;

    time_t inflationTime = (INFLATION_START_TIME + seq * INFLATION_FREQUENCY);
    if (closeTime < inflationTime)
    {
        metrics.NewMeter({"op-inflation", "failure", "not-time"}, "operation")
            .Mark();
        innerResult().code(INFLATION_NOT_TIME);
        return false;
    }

    /*
    Inflation is calculated using the following

    1. calculate tally of votes based on "inflationDest" set on each account
    2. take the top accounts (by vote) that get at least .05% of the vote
    3. If no accounts are over this threshold then the extra goes back to the 
       inflation pool
    */

    int64_t totalVotes = lcl.totalCoins;
    int64_t minBalance =
        bigDivide(totalVotes, INFLATION_WIN_MIN_PERCENT, TRILLION);

    std::vector<AccountFrame::InflationVotes> winners;
    auto& db = ledgerManager.getDatabase();

    AccountFrame::processForInflation(
        [&](AccountFrame::InflationVotes const& votes)
        {
            if (votes.mVotes >= minBalance)
            {
                winners.push_back(votes);
                return true;
            }
            return false;
        },
        INFLATION_NUM_WINNERS, db);

    int64 amountToDole =
        bigDivide(lcl.totalCoins, INFLATION_RATE_TRILLIONTHS, TRILLION);
    amountToDole += lcl.feePool;

    lcl.feePool = 0;
    lcl.inflationSeq++;

    // now credit each account
    innerResult().code(INFLATION_SUCCESS);
    auto& payouts = innerResult().payouts();

    int64 leftAfterDole = amountToDole;

   
    for (auto const& w : winners)
    {
        AccountFrame::pointer winner;

        int64 toDoleThisWinner =
            bigDivide(amountToDole, w.mVotes, totalVotes);

        if (toDoleThisWinner == 0)
            continue;

        winner = AccountFrame::loadAccount(w.mInflationDest, db);

        if (winner)
        {
            leftAfterDole -= toDoleThisWinner;
            lcl.totalCoins += toDoleThisWinner;
            winner->getAccount().balance += toDoleThisWinner;
            winner->storeChange(inflationDelta, db);
            payouts.emplace_back(w.mInflationDest, toDoleThisWinner);
        }
    }
   
    // put back in fee pool as unclaimed funds
    lcl.feePool += leftAfterDole;
    

    inflationDelta.commit();

    metrics.NewMeter({"op-inflation", "success", "apply"}, "operation").Mark();
    return true;
}
Пример #5
0
bool
InflationOpFrame::doApply(medida::MetricsRegistry& metrics, LedgerDelta& delta,
                          LedgerManager& ledgerManager)
{
    LedgerDelta inflationDelta(delta);

    auto& lcl = inflationDelta.getHeader();

    time_t closeTime = lcl.scpValue.closeTime;
    uint32_t seq = lcl.inflationSeq;

    time_t inflationTime = (INFLATION_START_TIME + seq * INFLATION_FREQUENCY);
    if (closeTime < inflationTime)
    {
        metrics.NewMeter({"op-inflation", "failure", "not-time"}, "operation")
            .Mark();
        innerResult().code(INFLATION_NOT_TIME);
        return false;
    }

    /*
    Inflation is calculated using the following

    1. calculate tally of votes based on "inflationDest" set on each account
    2. take the top accounts (by vote) that exceed 1.5%
        (INFLATION_WIN_MIN_PERCENT) of votes,
        up to 50 accounts (INFLATION_NUM_WINNERS)
    exception:
    if no account crosses the INFLATION_WIN_MIN_PERCENT, the top 50 is used
    3. share the coins between those accounts proportionally to the number
        of votes they got.
    */

    int64_t totalVotes = 0;
    bool first = true;
    int64_t minBalance =
        bigDivide(lcl.totalCoins, INFLATION_WIN_MIN_PERCENT, TRILLION);

    std::vector<AccountFrame::InflationVotes> winners;
    auto& db = ledgerManager.getDatabase();

    AccountFrame::processForInflation(
        [&](AccountFrame::InflationVotes const& votes)
        {
            if (first && votes.mVotes < minBalance)
            {
                // need to take the entire set if nobody crossed the threshold
                minBalance = 0;
            }

            first = false;

            bool res;

            if (votes.mVotes >= minBalance)
            {
                totalVotes += votes.mVotes;
                winners.push_back(votes);
                res = true;
            }
            else
            {
                res = false;
            }

            return res;
        },
        INFLATION_NUM_WINNERS, db);

    int64 amountToDole =
        bigDivide(lcl.totalCoins, INFLATION_RATE_TRILLIONTHS, TRILLION);
    amountToDole += lcl.feePool;

    lcl.feePool = 0;
    lcl.inflationSeq++;

    // now credit each account
    innerResult().code(INFLATION_SUCCESS);
    auto& payouts = innerResult().payouts();

    if (totalVotes != 0)
    {
        for (auto const& w : winners)
        {
            AccountFrame::pointer winner;

            int64 toDoleThisWinner =
                bigDivide(amountToDole, w.mVotes, totalVotes);

            if (toDoleThisWinner == 0)
                continue;

            winner = AccountFrame::loadAccount(w.mInflationDest, db);

            if (winner)
            {
                lcl.totalCoins += toDoleThisWinner;
                winner->getAccount().balance += toDoleThisWinner;
                winner->storeChange(inflationDelta, db);
                payouts.emplace_back(w.mInflationDest, toDoleThisWinner);
            }
            else
            {
                // put back in fee pool as unclaimed funds
                lcl.feePool += toDoleThisWinner;
            }
        }
    }
    else
    {
        // put back in fee pool as unclaimed funds
        lcl.feePool += amountToDole;
    }

    inflationDelta.commit();

    metrics.NewMeter({"op-inflation", "success", "apply"}, "operation").Mark();
    return true;
}
Пример #6
0
OfferExchange::CrossOfferResult
OfferExchange::crossOffer(OfferFrame& sellingWheatOffer,
                          int64_t maxWheatReceived, int64_t& numWheatReceived,
                          int64_t maxSheepSend, int64_t& numSheepSend)
{
    Asset& sheep = sellingWheatOffer.getOffer().buying;
    Asset& wheat = sellingWheatOffer.getOffer().selling;
    AccountID& accountBID = sellingWheatOffer.getOffer().sellerID;

    Database& db = mLedgerManager.getDatabase();

    AccountFrame::pointer accountB;
    accountB = AccountFrame::loadAccount(accountBID, db);
    if (!accountB)
    {
        throw std::runtime_error(
            "invalid database state: offer must have matching account");
    }

    TrustFrame::pointer wheatLineAccountB;
    if (wheat.type() != ASSET_TYPE_NATIVE)
    {
        wheatLineAccountB = TrustFrame::loadTrustLine(accountBID, wheat, db);
        if (!wheatLineAccountB)
        {
            throw std::runtime_error(
                "invalid database state: offer must have matching trust line");
        }
    }

    TrustFrame::pointer sheepLineAccountB;

    if (sheep.type() == ASSET_TYPE_NATIVE)
    {
        numWheatReceived = INT64_MAX;
    }
    else
    {
        sheepLineAccountB = TrustFrame::loadTrustLine(accountBID, sheep, db);
        if (!sheepLineAccountB)
        {
            throw std::runtime_error(
                "invalid database state: offer must have matching trust line");
        }

        // compute numWheatReceived based on what the account can receive
        int64_t sellerMaxSheep = sheepLineAccountB->getMaxAmountReceive();

        if (!bigDivide(numWheatReceived, sellerMaxSheep,
                       sellingWheatOffer.getOffer().price.d,
                       sellingWheatOffer.getOffer().price.n))
        {
            numWheatReceived = INT64_MAX;
        }
    }

    // adjust numWheatReceived with what the seller has
    {
        int64_t wheatCanSell;
        if (wheat.type() == ASSET_TYPE_NATIVE)
        {
            // can only send above the minimum balance
            wheatCanSell = accountB->getBalanceAboveReserve(mLedgerManager);
        }
        else
        {
            if (wheatLineAccountB->isAuthorized())
            {
                wheatCanSell = wheatLineAccountB->getBalance();
            }
            else
            {
                wheatCanSell = 0;
            }
        }
        if (numWheatReceived > wheatCanSell)
        {
            numWheatReceived = wheatCanSell;
        }
    }
    // you can receive the lesser of the amount of wheat offered or
    // the amount the guy has

    if (numWheatReceived >= sellingWheatOffer.getOffer().amount)
    {
        numWheatReceived = sellingWheatOffer.getOffer().amount;
    }
    else
    {
        // update the offer based on the balance (to determine if it should be
        // deleted or not)
        // note that we don't need to write into the db at this point as the
        // actual update
        // is done further down
        sellingWheatOffer.getOffer().amount = numWheatReceived;
    }

    bool reducedOffer = false;

    if (numWheatReceived > maxWheatReceived)
    {
        numWheatReceived = maxWheatReceived;
        reducedOffer = true;
    }

    // this guy can get X wheat to you. How many sheep does that get him?
    if (!bigDivide(numSheepSend, numWheatReceived,
                   sellingWheatOffer.getOffer().price.n,
                   sellingWheatOffer.getOffer().price.d))
    {
        numSheepSend = INT64_MAX;
    }

    if (numSheepSend > maxSheepSend)
    {
        // reduce the number even more if there is a limit on Sheep
        numSheepSend = maxSheepSend;
        reducedOffer = true;
    }

    // bias towards seller (this cannot overflow at this point)
    numWheatReceived =
        bigDivide(numSheepSend, sellingWheatOffer.getOffer().price.d,
                  sellingWheatOffer.getOffer().price.n);

    bool offerTaken = false;

    if (numWheatReceived == 0 || numSheepSend == 0)
    {
        if (reducedOffer)
        {
            return eOfferCantConvert;
        }
        else
        {
            // force delete the offer as it represents a bogus offer
            numWheatReceived = 0;
            numSheepSend = 0;
            offerTaken = true;
        }
    }

    offerTaken =
        offerTaken || sellingWheatOffer.getOffer().amount <= numWheatReceived;
    if (offerTaken)
    {   // entire offer is taken
        sellingWheatOffer.storeDelete(mDelta, db);

        accountB->addNumEntries(-1, mLedgerManager);
        accountB->storeChange(mDelta, db);
    }
    else
    {
        sellingWheatOffer.getOffer().amount -= numWheatReceived;
        sellingWheatOffer.storeChange(mDelta, db);
    }

    // Adjust balances
    if (sheep.type() == ASSET_TYPE_NATIVE)
    {
        accountB->getAccount().balance += numSheepSend;
        accountB->storeChange(mDelta, db);
    }
    else
    {
        if (!sheepLineAccountB->addBalance(numSheepSend))
        {
            return eOfferCantConvert;
        }
        sheepLineAccountB->storeChange(mDelta, db);
    }

    if (wheat.type() == ASSET_TYPE_NATIVE)
    {
        accountB->getAccount().balance -= numWheatReceived;
        accountB->storeChange(mDelta, db);
    }
    else
    {
        if (!wheatLineAccountB->addBalance(-numWheatReceived))
        {
            return eOfferCantConvert;
        }
        wheatLineAccountB->storeChange(mDelta, db);
    }

    mOfferTrail.push_back(
        ClaimOfferAtom(accountB->getID(), sellingWheatOffer.getOfferID(), wheat,
                       numWheatReceived, sheep, numSheepSend));

    return offerTaken ? eOfferTaken : eOfferPartial;
}
Пример #7
0
int64_t
OfferFrame::computePrice() const
{
    return bigDivide(mOffer.price.n, OFFER_PRICE_DIVISOR, mOffer.price.d);
}