```python
def retry_delays(attempts, base, cap):
    if isinstance(attempts, bool) or not isinstance(attempts, int):
        raise TypeError("attempts must be a non-negative integer")
    if attempts < 0:
        raise ValueError("attempts must be non-negative")
    if base < 0:
        raise ValueError("base must be non-negative")
    if cap < 0:
        raise ValueError("cap must be non-negative")
    
    result = []
    for i in range(attempts):
        # Compute base * 2**i without converting huge int to float
        # If base is 0, result is 0
        if base == 0:
            value = 0.0
        else:
            # Check if base * 2**i exceeds cap
            # We need min(cap, base * 2**i)
            # To avoid overflow, we can check if 2**i * base > cap
            # Since base is a float, we can compute iteratively or use logarithms
            # But simpler: if base * 2**i > cap, then value = cap
            # We can check: if base * (2**i) > cap, but 2**i can be huge.
            # Instead, we can compute the value step by step or use a check.
            # Let's use: if base * 2**i > cap, then value = cap
            # To avoid overflow, we can check if 2**i > cap / base (if base > 0)
            if base > 0:
                # Check if 2**i * base > cap
                # Equivalent to 2**i > cap / base
                # But cap / base might be float, and 2**i is int.
                # We can compute 2**i as int, but if i is large, 2**i is huge.
                # Instead, we can use logarithms or iterative multiplication.
                # Let's use iterative approach to avoid huge ints.
                # Actually, we can compute value = base * 2**i, but if i is large, 2**i is huge.
                # We can check if base * 2**i > cap by comparing 2**i > cap / base.
                # But cap / base is a float, and 2**i is an int.
                # If i is large enough that 2**i > cap / base, then value = cap.
                # We can compute threshold = cap / base
                # If 2**i > threshold, then value = cap
                # But 2**i can be huge. We can check if i > log2(threshold)
                # But log2 might have precision issues.
                # Alternative: compute value iteratively, but that's O(attempts).
                # Since attempts can be 10000, O(attempts) is fine.
                # Let's compute value iteratively to avoid huge ints.
                # Start with current = base
                # For each i, current = current * 2, but if current > cap, value = cap
                # But we need to handle base = 0 separately.
                # Let's use iterative approach.
                pass
            else:
                value = 0.0
        
        # Let's redo with iterative approach
        # Actually, let's just use iterative computation to avoid overflow
        # We'll compute value for each i iteratively
        # Start with current = base
        # For i=0, value = min(cap, base)
        # For i=1, value = min(cap, base * 2)
        # etc.
        # But we need to handle base = 0
        pass
    
    # Let's rewrite properly
    result = []
    current = base
    for i in range(attempts):
        if base == 0:
            value = 0.0
        else:
            # current = base * 2**i
            # We compute iteratively
            if i == 0:
                current = base
            else:
                current = current * 2
            if current > cap:
                value = cap
            else:
                value = current
        result.append(value)
    return result
```