The flink optimizer will basically do two things for you (+ some other magic regarding iterations which I will leave aside for now)
1) Algorithm selection: e.g., choose between a hash-join or merge-join;
2) Partitioning strategy: track grouping key, and if partitioning is needed, pick a suitable strategy (e.g. re-partition vs broadcast for a join);
Besides that the optimizer will fix the hyperparameters for your algorithms (e.g. memory allocation) and will ultimately generate the final program that has to be executed.