Il problema era che l'object
dtype è fuorviante. Ho pensato che significasse che tutti gli elementi erano stringhe. Ma a quanto pare, durante la lettura del file pandas stava convertendo alcuni elementi in ints e lasciando i resti come stringhe.
La soluzione era assicurarsi che ogni campo fosse una stringa:
>>> df1.col1 = df1.col1.astype(str)
>>> df2.col2 = df2.col2.astype(str)
Quindi l'unione funziona come previsto.
(Vorrei che ci fosse un modo per specificare un dtype
di str
...)