@SuppressWarnings("ConstantConditions")
    public boolean replaceActions(@NonNull Class<? extends Action> clazz, @NonNull Action a) {
        if (clazz == null) {
            throw new IllegalArgumentException("Action type must be non-null");
        }
        if (a == null) {
            throw new IllegalArgumentException("Action must be non-null");
        }
        // CopyOnWriteArrayList does not support Iterator.remove, so need to do it this way:
        List<Action> old = new ArrayList<>();
        List<Action> current = getActions();
        boolean found = false;
        for (Action a1 : current) {
            if (!found) {
                if (a.equals(a1)) {
                    found = true;
                } else if (clazz.isInstance(a1)) {
                    old.add(a1);
                }
            } else if (clazz.isInstance(a1) && !a.equals(a1)) {
                old.add(a1);
            }
        }
        current.removeAll(old);
        if (!found) {
            addAction(a);
        }
        return !(old.isEmpty() && found);
    }
@SuppressWarnings("deprecation")
    @Test
    public void replaceActions() {
        CauseAction a1 = new CauseAction();
        ParametersAction a2 = new ParametersAction();
        thing.addAction(a1);
        thing.addAction(a2);
        CauseAction a3 = new CauseAction();
        assertTrue(thing.replaceActions(CauseAction.class, a3));
        assertEquals(Arrays.asList(a2, a3), thing.getActions());
        assertFalse(thing.replaceActions(CauseAction.class, a3));
        assertEquals(Arrays.asList(a2, a3), thing.getActions());
    }