def isacn(obj):
    """isacn(string or int) -> True|False

    Validate an ACN (Australian Company Number).
    http://www.asic.gov.au/asic/asic.nsf/byheadline/Australian+Company+Number+(ACN)+Check+Digit

    Accepts an int, or a string of digits including any leading zeroes.
    Digits may be optionally separated with spaces. Any other input raises
    TypeError or ValueError.

    Return True if the argument is a valid ACN, otherwise False.

    >>> isacn('004 085 616')
    True
    >>> isacn('005 085 616')
    False

    """
    if isinstance(obj, int):
        if not 0 <= obj < 10**9:
            raise ValueError('int out of range for an ACN')
        obj = '%09d' % obj
        assert len(obj) == 9
    if not isinstance(obj, str):
        raise TypeError('expected a str or int but got %s' % type(obj))
    obj = obj.replace(' ', '')
    if len(obj) != 9:
        raise ValueError('ACN must have exactly 9 digits')
    if not obj.isdigit():
        raise ValueError('non-digit found in ACN')
    digits = [int(c) for c in obj]
    weights = [8, 7, 6, 5, 4, 3, 2, 1]
    assert len(digits) == 9 and len(weights) == 8
    chksum = 10 - sum(d*w for d,w in zip(digits, weights)) % 10
    if chksum == 10:
        chksum = 0
    return chksum == digits[-1]