Several optimizations from the method-opt branch

A bunch of optimizations, starting with a method representation change, that makes the compiler run significantly faster, and slightly improves the runtime of other programs (we still need better benchmarking to have a quantitative statement there).  But large programs in CPO compile up to twice as fast with these changes.

Major changes re: methods:

- Make the common representation of methods be a single function including the `self` argument.
- Add a new expression type, `method-app`, for expressions like `o.x(arg, ...)`, which is semantically identical (aside from performance), to a `dot` and an `app`.
- Compile expressions like `o.x(arg, ...)` to check if `o.x` is a method and apply the full function directly instead of currying first

Other optimizations:

- Favor string-dicts over lists and sets when checking string membership
- Add a fast path to equality so we don't need to allocate closures for a `safeCall` every time
- When possible, don't repeatedly perform `getField` on things in ffi-helpers
- Add `merge` and `keys-list` methods to string-dicts to more efficiently combine dicts, and to avoid calling `to-list` on sets when a set is the desired return type