Sí, si es un problema.
Si añades o eliminas elementos de un List o derivados (como ArrayList) mientras "iteras", el Iterador se quejará.
Se podría subsanar este problema creando sublistas temporales, una con elementos para añadir, otra con elementos para eliminar... y tras finalizar la iteración consultamos estas sublistas para actualizar el ArrayList principal añadiendo y quitando los elementos que correspondan y así la próxima vez que creemos el Iterator los cambios ya estarán hechos.
O bien, tras cada cambio realizado, volver a instanciar el Iterador para que este actualizado al momento. Esto cuando vayas aprendiendo a separar tu programa en subprogramas (métodos) que se encarguen de pequeñas tareas concretas, será más fácil de lo que parece.
Además normalmente preferirás dar opciones específicas al usuario:
1º Añadir Producto..
2º Eliminar Producto...
3º Mostrar listado de Productos actual...De modo que no te verás en la tesitura de "Añadir un Producto" durante el proceso de "Mostrar listado", ya que serán subprocesos distintos y para "Añadir Producto" no necesitas iterar, tan solo pedir datos, crear un objeto Producto y añadirlo al ArrayList.
Luego cuando el usuario eliga
opcion 3 "Mostrar Listado", en ese momento podrás crear un Iterador tranquilamente porque dentro de esta opción no vas a dar la posibilidad de añadir o eliminar productos.
Por otra parte, he de decir que no soy programador profesional ni por asomo. Soy poco más que un aprendiz algo avanzadillo...
Pero en realidad, nunca he necesitado usar iteradores para recorrer los ArrayList.
Suelo usar indices si van a haber modificaciones o si solo necesito recorrerlo para mostrar y computar datos, como es el caso de tu programa, uso un cómodo "
for each" y listo.
En definitiva, no te agobies con este "limitación" del Iterator, no solo hay formas de subsanarla, sino que en realidad posiblemente muy pocas veces necesites usar un iterador para moverte por los ArrayList.