Muy bien, vamos por partes.
- ¿Por qué es más fácil si "Nombre_alumno_n" va todo junto?
Muy simple. Porque es "una sola palabra". Entiéndase como una sola palabra que no va separado por espacios lo cual permite leerlo de otra forma, en vez de usando <getline()> podemos usar el operador >> como hacemos cuando ponemos < cin >> variable >.
En este caso lo que te propuse para evitar darle tantas vueltas a esto fue lo siguiente, si recuerdas:
Igual que antes copias las líneas pares pero antes intercalas esto:
file << "Nombre alumno " << contador << " Alumno " << contador++ << endl;
Inicializando contador en 1 para que vaya incrementándose en cada iteración.
Como conocíamos el formato de la línea podíamos escribirla nosotros sin necesidad de usar lo que habíamos leído. Pero imagina que desconocemos el formato, o que en algún momento cambiaremos el formato del fichero de entrada y cambiamos "Nombre alumno n" por "Nombre". Entonces tendríamos que cambiarlo en nuestro código si queremos que siga quedando igual.
En cambio si lo tenemos en una sola palabra (usando _) podemos leer esa primera palabra, copiarla en el fichero de salida y reemplazar el nombre únicamente. Para ello podemos leer palabra a palabra de la siguiente manera:
string palabra;
while(!fichero.eof())
fichero >> palabra;
No sé si lo ves. Si leyésemos la línea entera tendríamos que ver dónde empieza el nombre para ver dónde empezar a reemplazar. De esta forma leemos la primera palabra, la copiamos, leemos la segunda (para poder avanzar en el fichero) pero la obviamos y reemplazamos por lo que nosotros queramos poner. También podemos leer el nombre si fuera una sola palabra y modificar el <string> que almacena el nombre y volver a guardarlo. Por hacerlo menos manual.
Esto que te comento se ve mucho mejor en la otra línea, en la que se encuentran las notas. Si leemos la línea entera pues luego tendríamos que calcular nosotros dónde empieza la nota para separarla y convertirla en un <double> por ejemplo y luego guardarla en otra variable para poder trabajar con ella... En definitiva, un rollo
Al poder leer por palabras podemos guardar la primera en un <string> que sea siempre el mismo ya que no lo necesitamos y la segunda palabra (la nota en este caso) en otra variable.
Para ello cómo te he comentado antes debemos usar el operador >> en lugar de <getline()>. Te pongo un ejemplo de cómo quedaría:
string palabra, linea; // linea es innecesaria, podemos usar la misma variable para todo pero es para verlo mejor
double notas[SIZE]; // si no trabajamos con memoria dinamica ponemos un SIZE suficientemente grande
int num_notas = 0;
while(!fichero.eof()){
getline(fichero, linea);
fichero >> palabra >> notas[num_notas++];
}
Con ese código vamos almacenando las líneas impares en línea (que son las que menos nos interesan ahora) y luego de las líneas pares guardamos la primera palabra (notas_alumno_n) en <palabra> y la nota en <notas>. Repito, como no estamos utilizando ni <linea> ni <palabra> para trabajar podemos usar la misma variable para ambas cosas, pero lo he puesto así para que fuera más visual.
Hecho esto tenemos en el array <notas> todas las notas almacenadas para trabajar con ellas y en la variable <num_notas> el número de notas que hemos almacenado para no recorrer el array entero en caso de que nos sobren posiciones.
Respecto a lo que has mencionado de la función <seekg()>, eso son funciones para acceso aleatorio de un fichero pero si estás empezando te recomiendo trabajar con acceso secuencial hasta que hayas cogido práctica al menos. Casi siempre tendrás que usar alguna variable "vertedero" donde ir dejando lo que no te interesa pero se como has visto, se puede hacer.
Espero que te sirva para completar tu programa. Suerte