'?' / 'is' get more useful with more complex predicate names than just 'valid', and they also help with certain corner cases in English. For example, what does the following code do:
if(widget.free()) { ... }
Does it 1) check if the widget is "free" (whatever that means in the widget domain), or 2) frees the widget and checks the outcome of that operation?
If I saw something like this while reading code, I'd pause and carefully check what exactly is going on here.
In fact, I was going to write "Option 2) resembles resource management patterns, for example memory management in C", but then I checked and noticed that free() in C does not return a value, so this pattern would not exist with malloc()/free() - in other words, despite doing a bit of C and a lot of C++ in the past two decades, I still tripped over this.
Now compare with:
if(widget.isFree()) { ... }
if(widget.free?()) { ... }
Both resolve this ambiguity.
On that note, I'd love some kind of sigil for "asserting" functions - which are similar to checks, but instead of returning true/false, they ensure the argument is in the state described by the function name, or else they throw an exception. It's a pattern I've been using in exception-ful code to cut down on noise. For example:
// Check if connected; if not, maybe run reconnection
// logic or attempt some other form of recovery.
// The only way control proceeds past this line is if
// the session is connected; if it isn't and can't be,
// exception is thrown.
EnsureConnected(session);
if(IsSomething(session, arg1)) {
// ... some code requiring connected session
}
// ... more code requiring connected session
It's not a big deal, but in some cases, that "Ensure" or "Assert" look weird, and I don't like inventing more synonyms for the same pattern.