Python
Python is where almost all my analysis and backend code lives. The honest reason is not the language, which has real weaknesses, but the scientific ecosystem — NumPy, pandas, Xarray, matplotlib, SciPy, and the geospatial stack. For climate work there is no comparable alternative, and the ecosystem is the deciding factor by a wide margin.
What it is good at
The array stack is the substance. NumPy makes vectorised numerical work fast despite the interpreter, because the loops happen in compiled code. Xarray adds labelled dimensions, so selecting a region is ds.sel(lat=slice(-10, 10)) rather than index arithmetic — clearer and much less prone to the silent off-by-one errors that index-based slicing produces.
Its readability genuinely matters in research code, which is usually written by one person and read by another later, often with no software engineering background. Code that can be followed by a domain scientist is worth a great deal, and it is the reason Python displaced more capable languages here.
What it is bad at
Speed, when you cannot vectorise. A Python loop over millions of elements is orders of magnitude slower than compiled code. Usually the answer is expressing it as an array operation; where the algorithm genuinely does not vectorise, the answer is Numba, Cython, or dropping to another language. Pretending the problem does not exist produces analysis that takes overnight and should take a minute.
The GIL. Only one thread executes Python bytecode at a time, so threading does not parallelise CPU work — that needs multiprocessing or a library releasing the GIL internally, as NumPy does. This also underlies the async trap, where a blocking call stalls the entire event loop.
Dependency management. Multiple overlapping tools, and environments that break in ways that are hard to diagnose. This is the most common obstacle to reproducing someone else’s analysis, which is why Binder and declarative environments through devenv matter more than they should have to.
Typing
Type hints are optional and worth using. They are not enforced at runtime unless something like Pydantic does it, and their value is in tooling — a type checker catches a whole class of error before the code runs, which matters most in analysis code where a wrong result looks like a result.
See also: Python tips, Pydantic, FastAPI, Pangeo, and Node.js for the comparison.