Created
August 6, 2014 01:34
-
-
Save anonymous/e1f2dfb2b5b8d8a87aec to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import random | |
import numpy | |
class EconomicsFucked(Exception): pass | |
class NotEnoughBitcoin(EconomicsFucked): pass | |
class NotEnoughDollars(EconomicsFucked): pass | |
class PriceTooHigh(EconomicsFucked): pass | |
class PriceTooLow(EconomicsFucked): pass | |
class UBA: | |
def __init__(self, initialdollars, initialbitcoin, initialprice, commission): | |
self.dollars = initialdollars | |
self.bitcoin = initialbitcoin | |
self.prices = [initialprice] | |
self.commission = commission | |
def check_price(self): | |
return self.prices[-1] | |
def is_price_higher_than(self, wantedprice): | |
return self.prices[-1] > wantedprice | |
def is_price_lower_than(self, wantedprice): | |
return self.prices[-1] < wantedprice | |
def accept_bitcoin_dispense_dollars(self, bitcoinamount): | |
dollaramount = bitcoinamount * self.prices[-1] | |
dollaramount = dollaramount * (1. - self.commission) | |
if self.dollars < dollaramount: | |
raise NotEnoughDollars() | |
self.bitcoin = self.bitcoin + bitcoinamount | |
self.dollars = self.dollars - dollaramount | |
return dollaramount | |
def accept_dollars_dispense_bitcoin(self, dollaramount): | |
bitcoinamount = dollaramount / self.prices[-1] | |
bitcoinamount = bitcoinamount * (1. - self.commission) | |
if self.bitcoin < bitcoinamount: | |
raise NotEnoughBitcoin() | |
self.dollars = self.dollars + dollaramount | |
self.bitcoin = self.bitcoin - bitcoinamount | |
return bitcoinamount | |
def report(self): | |
print "------------------------" | |
print "Dollars: %.2f" % self.dollars | |
print "BTC: %.5f" % self.bitcoin | |
print "Price: %.2f" % self.prices[-1] | |
print "Net worth first price: %.2f" % (self.dollars + (self.bitcoin * self.prices[0])) | |
print "Net worth last price: %.2f" % (self.dollars + (self.bitcoin * self.prices[-1])) | |
class BitcoinSellr: | |
def __init__(self, target_bitcoin_price, bitcoinamount): | |
self.bitcoinamount = bitcoinamount | |
self.targetprice = target_bitcoin_price | |
def behave(self, uba): | |
if uba.is_price_lower_than(self.targetprice): | |
raise PriceTooLow() | |
uba.accept_bitcoin_dispense_dollars(self.bitcoinamount) | |
class BitcoinBuyer: | |
def __init__(self, target_bitcoin_price, dollaramount): | |
self.dollaramount = dollaramount | |
self.targetprice = target_bitcoin_price | |
def behave(self, uba): | |
if uba.is_price_higher_than(self.targetprice): | |
raise PriceTooHigh() | |
uba.accept_dollars_dispense_bitcoin(self.dollaramount) | |
def puppeteer(): | |
initialprice = 650. | |
uba = UBA(10000., 10, 650.0, 0.01) | |
buyerprices = numpy.random.poisson(initialprice, 1000) | |
buyeramounts = numpy.random.poisson(350, 1000) | |
sellerprices = numpy.random.poisson(initialprice, 1000) | |
selleramounts = numpy.random.poisson(50, 1000) * 0.01 | |
buyers = [BitcoinBuyer(price, amount) for price,amount in zip(buyerprices, buyeramounts)] | |
sellers = [BitcoinSellr(price, amount) for price,amount in zip(sellerprices, selleramounts)] | |
customers = buyers + sellers | |
random.shuffle(customers) | |
uba.report() | |
for customer in customers: | |
try: | |
customer.behave(uba) | |
if isinstance(customer,BitcoinBuyer): | |
print "%s spent %.2f to get BTC at price %.2f" % (customer.__class__.__name__, customer.dollaramount, uba.check_price()) | |
elif isinstance(customer,BitcoinSellr): | |
print "%s put up %.5f to get dollars at price %.2f" % (customer.__class__.__name__, customer.bitcoinamount, uba.check_price()) | |
else: | |
assert 0, "not reached" | |
except EconomicsFucked, e: | |
if isinstance(e, PriceTooHigh): | |
print "%s thought %.2f was too high, wanted at most %.2f" %(customer.__class__.__name__, uba.check_price(), customer.targetprice) | |
elif isinstance(e, PriceTooLow): | |
print "%s thought %.2f was too low, wanted at least %.2f" %(customer.__class__.__name__, uba.check_price(), customer.targetprice) | |
elif isinstance(e, NotEnoughBitcoin): | |
print "%s wanted %.2f dollars converted to BTC but UBA only has %.5f BTC" %(customer.__class__.__name__, customer.dollaramount, uba.bitcoin) | |
elif isinstance(e, NotEnoughDollars): | |
print "%s wanted %.5f BTC converted to dollars but UBA only has %.2f dollars" %(customer.__class__.__name__, customer.bitcoinamount, uba.dollars) | |
else: | |
assert 0, "not reached" | |
uba.report() | |
def main(): | |
puppeteer() | |
if __name__ == '__main__': | |
main() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment