wattpad tag sobre preguntas plantilla para lista incomodas hacer divertidas cosas con amigos c for-loop

tag - ¿Cuál es la mejor manera de hacer un ciclo inverso ''para'' con un índice sin firmar?



tags para hacer con amigos (20)

¿Por qué no simplemente?

unsigned int i = n; while(i--) { // use i }

Esto cumple con todos los requisitos enumerados en el cuerpo de la pregunta. No utiliza nada que pueda fallar en la revisión del código o que viole un estándar de codificación. La única objeción que pude ver es si el OP realmente insistió en un bucle for y no una manera directa de generar i = (n-1) .. 0.

Mi primer intento de reverse for loop que hace algo n veces fue algo así como:

for ( unsigned int i = n-1; i >= 0; i-- ) { ... }

Esto falla porque en la aritmética sin signo i se garantiza que siempre será mayor o igual que cero, por lo tanto, la condición de bucle siempre será verdadera. Afortunadamente, el compilador gcc me advirtió sobre una "comparación inútil" antes de que tuviera que preguntarme por qué el ciclo se estaba ejecutando infinitamente.

Estoy buscando una forma elegante de resolver este problema, teniendo en cuenta que:

  1. Debería ser un ciclo hacia atrás para.
  2. El índice de ciclo debe estar sin signo.
  3. n es constante sin signo.
  4. No debe basarse en la aritmética de anillo "oscura" de enteros sin signo.

¿Algunas ideas? Gracias :)


Como este no es un estándar para el bucle, probablemente usaría un bucle while, por ejemplo:

unsigned int i = n - 1; while (1) { /* do stuff with i */ if (i == 0) { break; } i--; }


Esto no se ha probado, pero podría hacer lo siguiente:

for (unsigned int i, j = 0; j < n; i = (n - ++j)) { /* do stuff with i */ }


Fácil, solo pare en -1:

for( unsigned int i = n; i != -1; --i ) { /* do stuff with i */ }

editar: no estoy seguro de por qué esto se está volviendo downvoted. funciona y es más simple y más obvio que cualquiera de los anteriores.


Hm. Estas son sus opciones:

  1. Use i=0 como condición de ruptura: el bucle no se ejecutará cuando llegue a 0, por lo tanto, ejecute 1 iteración del contenido del bucle para i=0 después de que el bucle haya salido.

for ( unsigned int i = n-1; i > 0; i-- ) { doStuff(i); } doStuff(0);

  1. En el ciclo, prueba i=0 y break . No recomendado porque ahora estás probando el valor de i dos veces en el ciclo. También el uso de ruptura dentro de un bucle generalmente se considera una mala práctica.

for ( unsigned int i = n-1; i >= 0; i-- ) { doStuff(i); if (i=0) break; }


La única razón por la que menciono esta opción es porque no la vi en la lista.

for ( unsigned int i = n-1; i < n; i-- ) { ... }

Totalmente en contra de la intuición, pero funciona. la razón por la que funciona es porque al restar 1 de 0 se obtiene el mayor número que se puede representar con un entero sin signo.

En general, no creo que sea una buena idea trabajar con enteros sin signo y arthmetic, especialmente al restar.


O puede confiar en el comportamiento de unsigned int de unsigned int si necesita indexar de n-1 a 0

for(unsigned int i = n-1; i < n; i--) { ... }


Qué tal si:

for (unsigned i = n ; i-- > 0 ; ) { // do stuff with i }


Quizás de esta manera? En mi humilde opinión, es claro y legible. Puede omitir el if (n> = 1) si se conoce implícitamente de alguna manera.

if(n>=1) { // Start the loop at last index unsigned int i = n-1; do { // a plus: you can use i, not i-1 here } while( i-- != 0 ); }

Otra version:

if(n>=1) { unsigned int i = n; do { i--; } while( i != 0 ); }

El primer código sin la declaración if se vería así:

unsigned int i = n-1; do { } while( i-- != 0 );


Tiendo a usar

for ( unsigned int i = n; i > 0; ) { --i; ... }

es casi lo mismo que la respuesta de skizz, (se pierde un decremento innecesario final, pero el compilador debe optimizar eso), y en realidad pasará la revisión del código. Cada estándar de codificación con el que he tenido que trabajar ha tenido una no mutación en la regla condicional.


Use dos variables, una para contar hacia arriba , y la otra para el índice de matriz:

unsigned int Index = MAX - 1; unsigned int Counter; for(Counter = 0; Counter < MAX; Counter++) { // Use Index Index--; }


ez:

#define unsigned signed for ( unsigned int i = n-1; i >= 0; i-- ) { ... }


for ( unsigned int i = n-1; (n-i) >= 0; i-- ) { // n-i will be negative when the loop should stop. ... }


for ( unsigned int i = n; i != 0; i-- ) { // do something with i - 1 ... }

Tenga en cuenta que si usa tanto C ++ como C, usar! = Es un buen hábito al que recurrir cuando utiliza iteradores, donde <= etc. puede no estar disponible.


for ( unsigned int i = n; i > 0; i-- ) { ... i-1 //wherever you''ve been using i }


for ( unsigned int i = n; i > 0; i-- ) { ... }

Debería funcionar bien Si necesita usar la variable i como índice en una matriz, hágalo así:

array[i-1];


for ( unsigned int i = n; i > 0; i-- ) { unsigned int x = i - 1; // do whatever you want with x }

Ciertamente no es elegante, pero funciona.


for ( unsigned int loopIndex = n; loopIndex > 0; --loopIndex ) { unsigned int i = loopIndex - 1; ... }

o

for ( unsigned int loopIndex = 0; loopIndex < n; ++loopIndex ) { unsigned int i = n - loopIndex - 1; ... }


for (unsigned int i = n-1; i<(unsigned int)-1; i--)

OK, es "aritmética de anillo oscuro".


unsigned index; for (unsigned i=0; i<n; i++) { index = n-1 - i; // {i == 0..n-1} => {index == n-1..0} }