[ Foro de Pascal ]
cordial saludo profesor Nacho Cabanes, gracia por atendernos siempre con tanta amabilidad y tanta ayuda.
profesor es que queria me ayudaras a convertir un codigo que realice , y que me funciona ok, pero al intentar llevarlo a una estructura while y repeat, al ejecutarlo me hace bucle infinito y pues quisiera que me indicaras como podria hacerlo.
el fragmento es:
procedure lo_ que_sea(parametros.., numpart..)
var
tiempo:tiempos;
i:integer;
begin
for i:=1 to numpart do
begin
if (c[i].pais=pais) then
begin
tiempo[i]:=calculartiempo(parametros..);
writeln('.........');
end;
end;
end;
como llevo el anterior fragmento a una estrutura while y repeat?
la condicion que debe cumplirse en cualquiera de los dos bucles mencionados es que c[i].pais= pais
en el repeat logicamente que para detener su ciclo seria, repita hasta que c[i].pais<>pais, pero el problema es que lo he intentado y en la ejecucion se desborda.
por favor no tenga en cuenta los parametros en cuenta da igual,lo que me interesa es llevar ese bloque a un bloque while y repeat.
mil gracias por su ayuda como siempre y su valioso tiempo y paciencia.
Espero que Nacho no se enoje si te respondo yo :)
Tu código quedaría así:
procedure lo_ que_sea(parametros.., numpart..)
var
tiempo:tiempos;
i:integer;
begin
i := 1;
repeat
if (c[i].pais=pais) then
begin
tiempo[i]:=calculartiempo(parametros..);
writeln('.........');
end;
inc(i); // ó i := i+1
until i > numpart;
end;
La diferencia fundamental entre el repeat y el for es que el repeat se ejecuta SIEMPRE al menos una vez, no importa el valor de inicio ni la condición. Saludos!
Gracias Jose por tu aporte, esta ok, el problema que tenia es que yo hacia esto, no me daba cuenta, siendo tan sencillo, jeje gracias.
procedure lo_ que_sea(parametros.., numpart..)
var
tiempo:tiempos;
i:integer;
begin
i := 1;
repeat
if (c[i].pais=pais) then
begin
tiempo[i]:=calculartiempo(parametros..);
writeln('.........');
end;
inc(i); // ó i := i+1
until (c[i].pais<>pais);
end;
como veis , el problema estaba en el until.pero gracias a ti me di cuenta de ello gracias.
cordial saludo profesor Nacho Cabanes.
profesor queria preguntarte que tengo que corregir o hacer para que el codigo me pregunte cada vez que el pais sea distinto al que se encuentre en la estructura, por uno nuevo, y que logicamente me procese lo demas una vez introduzca un pais que si esté en la estructura:
lo he intentado de esta DOS formas pero cuando digito porejemplo:
digite un pais:italia (que no esta )
digite un nuevo pais: españa ( que si está , aun asi me sigue preguntando: digite un nuevo pais, vamos que se queda el ciclo infinito)
FORMA 1:
en el program principal tengo:
...
...
writeln('introduzca la nacionalidad de la persona: ');
readln(c[i].pais);
posiciones_por pais(c,numpart,pais);
procedure posiciones_por_pais(var c:carrera;numpart:integer;pais:cadena);
var
tiempo:tiempos;
i:integer;
begin
i:=1;
repeat
if c[i].pais=pais then
begin
tiempo[i]:=calculartiempo(parametros);
writeln('...............');
end
else
begin
writeln('no esta el pais');
writeln('digite un nuevo pais : ');
readln(c[i].pais)
end;
inc(i);
until (i>numpart);
end;
****************************************************************
FORMA 2.
en el program principal tengo:
...
...
writeln('introduzca la nacionalidad de la persona: ');
readln(c[i].pais);
posiciones_por pais(c,numpart,pais);
procedure posiciones_por_pais(var c:carrera;numpart:integer;pais:cadena);
var
tiempo:tiempos;
i:integer;
begin
i:=1;
repeat
repeat
if c[i].pais=pais then
begin
tiempo[i]:=calculartiempo(parametros);
writeln('...............');
end;
inc(i);
until (i>numpart);
writeln('no esta el pais');
writeln('digite un nuevo pais : ');
readln(c[i].pais)
until (c[i].pais<>pais);
end;
por tu ayuda mil gracias profesor.
La forma de volver a pedir un dato ya existente es la que hemos comentado en el hilo "vector de numeros aleatorios con restriccion":
- Pides dentro de un "repeat-until", y, para cada nuevo valor, recorres los anteriores con "for", para asegurarte de que no se han usado con anterioridad.
Si no lo consigues, publica un fuente, lo más sencillo que puedas, pero a la vez "completo": capaz de compilar, para que podamos hacer pruebas rápidas y ayudarte con la parte que falle.
buenas tardes profesor Nacho cabanes.profesor desde el respecto que me merece Ud. perdoneme es que tu respuesta anterior a este hilo no es lo que queria pedirte en tu ayuda, seguro que me hice entender mal y te pido disculpas por ello. me refiero a que lo que me dices del vector de numeros aleatorios con restriccion, no es referente a lo que pregunto en el codigo que te inclui,pues ese hilo del vector aleatorio con retriccion ya lo solucione y tambien gracias a ti, sin embargo y permitamelo por favor a lo que me refiero en mi pregunta es respecto a lo siguiente:
en el program principal tengo:
...
...
writeln('introduzca la nacionalidad de la persona: ');
readln(c[i].pais);
posiciones_por pais(c,numpart,pais);
...
procedure posiciones_por_pais(var c:carrera;numpart:integer;pais:cadena);
var
tiempo:tiempos;
i:integer;
begin
i:=1;
repeat
if c[i].pais=pais then
begin
tiempo[i]:=calculartiempo(parametros);
writeln('...............');
end
inc(i);
until (i>numpart);
end;
mi pregunta profesor es con este codigo que tengo y que me va ok en el programa que estoy realizando, quiero mejorarlo en el aspecto de que me permita cuando la condicion dentro del procedimiento ( posiciones_por_pais ):
...
if c[i].pais=pais then
....
no se cumpla, es decir que el pais que se digito por pantalla desde el programa principal ,al llegar a este if del procedimiento en mencion , me permita volver a pedir uno nuevo, sin necesidad de terminar la ajecucion, sino en ese mismo instante.porejemplo:
en pantalla me pide el pais:
porejemplo ,digito España ( al no estar) me saliera:
el pais no se encuentra, digite otro pais por favor:
y al entrar ese nuevo pais que si esta ejecute nuevamente el ciclo del repeat( para que vuelva desde el inicio a buscar con ese nuevo pais)dentro del procedimiento(posiciones_por_pais):
...
i:=1;
repeat
if c[i].pais=pais then
begin
tiempo[i]:=calculartiempo(parametros);
writeln('...............');
end
inc(i);
until (i>numpart);
......
espero haberme hecho entender y mil gracias por atender siempre nuestras dudas y poder ayudarme en indicarme que deberia anexar dentro del procedimiento para que pueda lograr mi intencion.mil gracias profesor.
Entonces, si no he entendido mal, la duda sería cómo hacer que te vuelva a pedir el país si tecleas uno que no está en la lista.
Una recomendación: busca siempre la forma más legible de conseguirlo, y eso suele implicar el uso de funciones auxiliares.
Podría ser algo como
repeat
paisEscogido := pedirUnPais;
until pertenece(paisEscogido, listaDePaisesAceptables, cantidadPaisesAceptables);
c[i].pais = paisEscogido;
Donde "pedirUnPais" sería una función que devolvería una cadena de texto, así:
function pedirUnPais: string;
var
paisTemp: string;
begin
writeln('introduzca la nacionalidad de la persona: ');
readln(paisTemp);
pedirUnPais := paisTemp;
end;
Y "pertenece" sería una función que devolvería "true" si ese país que se ha escogido pertenece a una lista, la de los países aceptables, así:
function pertenece(pais: string, lista: listaPaises, cantidadPaises: integer): boolean;
var
encontrado: boolean;
i: integer
begin
encontrado := false;
for i:= 1 to cantidadPaises
begin
if pais = listaPaises[i] then encontrado := true;
end;
pertenece := encontrado;
end;
La lógica exacta (y la sintaxis exacta incluso) dependerán de tu problema concreto, pero espero que te den ideas.
(No se puede continuar esta discusión porque tiene más de dos meses de antigüedad. Si tienes dudas parecidas, abre un nuevo hilo.)