We all know when using Collections.synchronizedXXX (e.g. synchronizedSet()) we get a synchronized \"view\" of the underlying collection.
Ho
Depends on your access model. If you have low concurrency and frequent writes, 1 will have the best performance. If you have high concurrency with and infrequent writes, 3 will have the best performance. Option 2 is going to perform badly in almost all cases.
foreach calls iterator(), so exactly the same things apply.