Ayuda Codigo C

1, 2, 3
Ferdy escribió:Si seguis haciendo los deberes de la gente no aprenderán nunca. Es mejor (pero más dificil) dar pistas.


Hacer los deberes sería ponerle el código completo, no intentar explicarle cómo llegar a solucionar un problema. Digo yo :)

Aquí paz y después gloria.
Hola, me podeis ayudar a plantear esto? quiero decir, no es ayuda sobre el codigo, si no, que no se como hacer una comparacion del caracter que introduzco con la tabla ASCII.

Escribe un programa en C que, dada una variable de tipo carácter indique si el valor de la mima es un carácter alfabético, numérico o especial. Utiliza la tabla de caracteres ASCII.

Como es esa comparacion? existe algun modo en c en que yo pueda hacer una comparacion con la tabla, porq la tabla ya esta iguardada previamente?

Gracias, gracias, gracias.
Crapos escribió:Hola, me podeis ayudar a plantear esto? quiero decir, no es ayuda sobre el codigo, si no, que no se como hacer una comparacion del caracter que introduzco con la tabla ASCII.

Escribe un programa en C que, dada una variable de tipo carácter indique si el valor de la mima es un carácter alfabético, numérico o especial. Utiliza la tabla de caracteres ASCII.

Como es esa comparacion? existe algun modo en c en que yo pueda hacer una comparacion con la tabla, porq la tabla ya esta iguardada previamente?

Gracias, gracias, gracias.


Dependiendo del valor del carácter ASCII (que es un byte), puedes saber que tipo de carácter es.. por ejemplo, las mayúsculas van del 65 al 90, las minúsculas del 97 al 122, a partir del 128 son los caracteres extendidos... etc...

Echa un vistazo en: http://www.asciitable.com/
en c puedes comparar caracteres, por ejemplo

char c = leer(); // me da pereza escribir en c ahora
if (c >= 'a' and c <= 'z')
//entonces c es una letra minusculas

Ten cuidado por que 6 es diferente a '6'

Para hacer este ejericio no es necesario saber la tabla ascii, ni tenerla a mano
Veis, esa era la duda que tenia, y no sabia como hacerlo.
Muchas gracias a todos!!!
(mensaje borrado)
Buenas! Alguien me explica como hacer una función externa a partir de un Array? He estado probando cosas pero no me sale bien u__U

La cosa es que en el main, para probar, tengo esto:

#include <stdio.h>
#define N 10

int main() {

   int valor[N], indice, maxima;
   
   for (indice = 0; indice < N; indice++) {
     printf("Introduce el valor Nº%d: ", indice+1);
     scanf("%d", &valor[indice]);
   }
   printf("\n");

   /*Càlculo máximo*/
   maxima = valor[0];
   for (indice = 1; indice < N; indice++) {
     if (maxima < valor[indice]) {
       maxima = valor[indice];
     }
   }

Me gustaría tener una función externa para calcular el máximo, que entrada tiene que tener la función externa? O tengo que llenar el array dentro de ella? La verdad es que con valores normales las he hecho, pero con arrays pues no... una ayudita?
Simplemente, pasa el puntero al inicio del array, se hace igual que cuando lo creas. Por otro lado ten en cuenta que al trabajar con punteros, todos los pasos de array que hagas se harán por referencia, así que si haces algún cambio en el array desde la propia función, éste se verá reflejado fuera.
Debajo de donde incluyes las librerias:
int calcular_maximo(int arraydevalores[]); //array de valores y valor es el mismo vector pero no tiene porque llamarse igual aquí y en la funcion principal

en la funcion principal:

calcular_maximo(valor); //mandas el vector "valor" a la función


Ya despues desarrollas la funcion despues de la funcion principal:

int calcular_maximo(int arraydevalores[])
{
operaciones,etc....
}


No se si me abré equivocao en algo pero bueno espero que te ayude en algo, un saludo


PD: he declarado la funcion como "entero"(int) porque he supuesto que con un return devolverias un entero (el maximo)... pero eso ya son suposiciones mias xD, tambien puedes hacer un elemento de entrada/salida (puntero).
Gracias por la ayuda, aunque sigo sin saber hacerlo ^^" Os pongoel código que no funciona para que veáis que es lo que quiero hacer, así supongo que será más fácil decime lo que tengo mal (Y sí, ya se que está fatal xD Pero sólo he hecho una clase de punteros y de funciones externas voy bastante mal... u.u)

#include <stdio.h>
#include <stdlib.h>
#define N 10

int max(int *x) {
  int m,cont = 0;
 
  m = *x;
  for (cont = 0; cont < N; cont++) {
    if (m < *(x+cont)) {
      m = *(x+cont);
    }
  }
  return m;
}

int main() {

   int *p, cont;
   p=(int*)malloc(N*sizeof(int));
   
   for (cont = 0; cont < N; cont++) {
     printf("Introduce el valor Nº%d: ", cont+1);
     scanf("%d", p+cont);
   }
   
   printf("El máximo es %d\n",max(*p));
   }
puedes poner comentarios en el codigo? esque me estoy volviendo loco para entender:
x=(int*)malloc(N*sizeof(int));

xDDDDDD creo que se me escapa de mis conocimientos :(
Vale... se me ha escapado esa línea xD Era para probar cosas...

A ver... lo que quiero hacer es que yo asigno los valores en main, despues mando los valores a la función max para que trabaje con ellos, entonces mi método chustero es enviar el *p como variable a la función max, no sé si se entiende mi idea... u_u

Lo que no quiero es enviar la posición 2 o la posición 3, por decir algo, quiero enviar "todo el pack", para entendernos ^^"

Y esta p=(int*)malloc(N*sizeof(int)); en teoría si que está bien puesta y dice que reserve 10 espacios de memoria si no recuerdo mal
#include <stdio.h>
#include <conio.h>
main()
{
int x1=0;
int x2=0;
int y1=0;
int y2=0;
int pendiente=0;
printf("introduce x de la primera coordenada\n");
scanf("%d",&x1);
printf("introduce y de la primera coordenada\n");
scanf("%d",&y1);
printf("introduce x de la segunda coordenada\n");
scanf("%d",&x2);
printf("introduce y de la segunda coordenada\n");
scanf("%d",&y2);
pendiente=(y2-y1)/(x2-x1);
printf("la pendiente de las coordenadas (%d,%d) y (%d,%d) es:%.2f",x1,y1,x2,y2,pendiente);
getch();
}
aunque tambien lo puedes hacer con un for{}

pero todabia me falta en el valor de la pendiente no me sale bien la respuesta solo me sale 0.00 y noce si algo esta mal o es que el float no puede sacar valores negativo porque yo probe con cordenadas que dan una pendiente positiva y si me la saca pero luego probe con coordenadas que dan una pendiente negativa y siempre me sale 0.00 si me pueden guiar en eso que noce que es, el ejemplo que use para la pendiente negativa es (3,2) y (1,3) que seria con la ecuancion pendiente =(3-2)/(1-3) lo que da una pendiente de -0,5; y lo que quiero saber es como puedo hacer que me saque resultados negativo, porfa ayuda gracias de ante mano
pedro4949 escribió:#include <stdio.h>
#include <conio.h>
main()
{
int x1=0;
int x2=0;
int y1=0;
int y2=0;
int pendiente=0;
printf("introduce x de la primera coordenada\n");
scanf("%d",&x1);
printf("introduce y de la primera coordenada\n");
scanf("%d",&y1);
printf("introduce x de la segunda coordenada\n");
scanf("%d",&x2);
printf("introduce y de la segunda coordenada\n");
scanf("%d",&y2);
pendiente=(y2-y1)/(x2-x1);
printf("la pendiente de las coordenadas (%d,%d) y (%d,%d) es:%.2f",x1,y1,x2,y2,pendiente);
getch();
}
aunque tambien lo puedes hacer con un for{}

pero todabia me falta en el valor de la pendiente no me sale bien la respuesta solo me sale 0.00 y noce si algo esta mal o es que el float no puede sacar valores negativo porque yo probe con cordenadas que dan una pendiente positiva y si me la saca pero luego probe con coordenadas que dan una pendiente negativa y siempre me sale 0.00 si me pueden guiar en eso que noce que es, el ejemplo que use para la pendiente negativa es (3,2) y (1,3) que seria con la ecuancion pendiente =(3-2)/(1-3) lo que da una pendiente de -0,5; y lo que quiero saber es como puedo hacer que me saque resultados negativo, porfa ayuda gracias de ante mano

Declara pendiente como float, y en la linea:
pendiente=(y2-y1)/(x2-x1);
prueba a poner
pendiente=(float)(y2-y1)/(x2-x1);

Aquí lo tienes funcionando:
//Incluimos librerias a usar
#include <stdio.h>
#include <stdlib.h>
//Inicio de la función principal
main()
{
    int x1=0;
    int x2=0;
    int y1=0;
    int y2=0;
    float pendiente=0;

    //Pedimos datos por teclado
    printf("introduce x de la primera coordenada\n");
    scanf("%d",&x1);
    printf("introduce y de la primera coordenada\n");
    scanf("%d",&y1);
    printf("introduce x de la segunda coordenada\n");
    scanf("%d",&x2);
    printf("introduce y de la segunda coordenada\n");
    scanf("%d",&y2);
    //Realizamos la operacion
    pendiente=(float)(y2-y1)/(x2-x1);//Convertimos una operación de enteros a reales
    //Mostramos los datos por pantalla
    printf("la pendiente de las coordenadas (%d,%d) y (%d,%d) es:%.2f",x1,y1,x2,y2,pendiente);

system("pause");
return 0;
//Fin de la funcion principal
}
@Serginius: Tu código es correcto, sin embargo en la invocación a max, lo que haces es pasarle el contenido a lo que apunta p (*p) y al tratarse de un array esto no funciona ya que debes pasarle el puntero en sí (p), así que cambia el max(*p) por max(p) y ya te debería de funcionar.

Una duda que me ha surgido. Porque reservas así la memoria para el puntero?
No podrías haber hecho:
int *p, int array[N], cont;
p = &array[0];

?
Aunque supongo que lo tuyo será mas eficiente, no lo se :p

pedro4949 escribió:#include <stdio.h>
#include <conio.h>
main()
{
int x1=0;
int x2=0;
int y1=0;
int y2=0;
int pendiente=0;
printf("introduce x de la primera coordenada\n");
scanf("%d",&x1);
printf("introduce y de la primera coordenada\n");
scanf("%d",&y1);
printf("introduce x de la segunda coordenada\n");
scanf("%d",&x2);
printf("introduce y de la segunda coordenada\n");
scanf("%d",&y2);
pendiente=(y2-y1)/(x2-x1);
printf("la pendiente de las coordenadas (%d,%d) y (%d,%d) es:%.2f",x1,y1,x2,y2,pendiente);
getch();
}
aunque tambien lo puedes hacer con un for{}

pero todabia me falta en el valor de la pendiente no me sale bien la respuesta solo me sale 0.00 y noce si algo esta mal o es que el float no puede sacar valores negativo porque yo probe con cordenadas que dan una pendiente positiva y si me la saca pero luego probe con coordenadas que dan una pendiente negativa y siempre me sale 0.00 si me pueden guiar en eso que noce que es, el ejemplo que use para la pendiente negativa es (3,2) y (1,3) que seria con la ecuancion pendiente =(3-2)/(1-3) lo que da una pendiente de -0,5; y lo que quiero saber es como puedo hacer que me saque resultados negativo, porfa ayuda gracias de ante mano

Tu tienes un lio tremendo.

Lo primero... para que incluyes conio?? Si es por la última instrucción pon un system("pause") y arreando.
Lo segundo. Declaras todas las variables como int, y sin embargo luego en el printf pretendes mostrar 2 decimales de dividir 1 entero entre 1 entero... ¿?
Por último, no te muestra negativos porque solo muestra enteros, y el entero en ese caso es el 0.

En resumen, que cambies todas las variables a tipo float (y también haz todos los cambios que ello conlleve)

EDITO: Lo de Iverson88 también es correcto. Mi solución sirve ya de paso por si quieres meter coordenadas con decimales XD
Puyover escribió:Tu código es correcto, sin embargo en la invocación a max, lo que haces es pasarle el contenido a lo que apunta p (*p) y al tratarse de un array esto no funciona ya que debes pasarle el puntero en sí (p), así que cambia el max(*p) por max(p) y ya te debería de funcionar.


Pues creo que no ha funcionado, al compilar no me sale error pero si después pongo que "imprima" *(x+1) por ejemplo para probar, me pone en el compilador que "crea un puntero desde un entero" o algo así :/

Puyover escribió:Una duda que me ha surgido. Porque reservas así la memoria para el puntero?
No podrías haber hecho:
int *p, int array[N], cont;
p = &array[0];

?
Aunque supongo que lo tuyo será mas eficiente, no lo se :p

Yo tampoco lo sé xD Lo he hecho así porque es como salía en un ejemplo de punteros que nos han puesto.
Serginius escribió:Vale... se me ha escapado esa línea xD Era para probar cosas...

A ver... lo que quiero hacer es que yo asigno los valores en main, despues mando los valores a la función max para que trabaje con ellos, entonces mi método chustero es enviar el *p como variable a la función max, no sé si se entiende mi idea... u_u

Lo que no quiero es enviar la posición 2 o la posición 3, por decir algo, quiero enviar "todo el pack", para entendernos ^^"

Y esta p=(int*)malloc(N*sizeof(int)); en teoría si que está bien puesta y dice que reserve 10 espacios de memoria si no recuerdo mal

Según lo que me a parecido entender que quieres conseguir (rellenar un array con valores y que te calcule la máxima usando funciones) te he hecho el código comentado para que lo entiendas, si no entiendes pregunta ;)
//Declaracion de librerias y valores predefinidos
#include <stdio.h>
#include <stdlib.h>
#define N 10
//declaracion de variables
void introducir_valores_array(int valor[]);
int calcular_maximo(int valor[]);
//Funcion principal
int main()
{
    //Declaracion de variables de la funcion principal
   int valor[N], maxima;
   //Mandamos un vector de numeros enteros a la funcion encarga de dar valores
   introducir_valores_array(valor);
   /*Guardamos en la variable "maxima", el maximo obtenido en
   la funcion calcular maximo, que tiene como atributo el vector "valor"*/
   maxima=calcular_maximo(valor);
   //Mostramos el maximo por pantalla
   printf("La maxima es: %i \n",maxima);
   
   system("pause");
   return 0;
   //Fin de la funcion principal
}
   //Desarrollo de funciones
void introducir_valores_array(int valor[])
{
    int i=0;
    for(i=0;i<N;i++)
    {
        //Vamos pidiendo valores para rellenar el vector
        printf("Introduce el valor para posicion %i : \n",i+1);
        _flushall();
        //Los guardamos en la posicion correspondiente
        scanf("%i",&valor[i]);
    }
}
int calcular_maximo(int valor[])
{
    int maxima=0;
   
    maxima=valor[0];//Iniciamos el valor de la maxima con el primer valor del vector
    int i=0;
    for(i=0;i<N;i++)
    {
        if(valor[i]>maxima)//Si el dato que se guarda en la posicion "i" del vector es mayor a la maxima....
        {
            maxima=valor[i];//ese valor pasa a ser la nueva maxima
        }
    }
    return maxima;//devolvemos el ultimo valor asignado a la maxima a la funcion principal
}
No entiendo porque declaras las funciones como variables globales :/

Concretamente esto:

//declaracion de variables
void introducir_valores_array(int valor[]);
int calcular_maximo(int valor[]);

Lo demás lo tengo casi igual
si te das cuenta, están antes de la función principal, es la declaración.Luego en la función principal se "llaman" a las funciones, y al final de la función principal las desarrollas.
el int, void, float,etc... que pueda ir al principio de la declaración de la función es acorde al tipo de valor que se devuelve.
Por ejemplo void introducir_valores_array(int valor[]); no devuelve nada (con un return) ya que el array/puntero apunta a una dirección de memoria(apunta al mismo sitio dentro y fuera de la funcion,no se maneja la variable sino la dirección).
int calcular_maximo(int valor[]); => devuelve con el máximo con el return y es un entero, de ahí el int

PD: esa es la estructura con la que me han enseñado a mi, quizás haya más formas.
Serginius escribió:No entiendo porque declaras las funciones como variables globales :/

Concretamente esto:

//declaracion de variables
void introducir_valores_array(int valor[]);
int calcular_maximo(int valor[]);

Lo demás lo tengo casi igual

http://www.mailxmail.com/curso-informat ... -funciones

Saludos:).
Vale, ya lo entiendo, pero ahora tengo el siguiente código y no me sale me pone violación del segmento al poner el 4 valor, he mirado y creo que en teoría lo tengo todo bien ,a ver si lo veis vosotros...

#include <stdio.h>
#include <stdlib.h>
#define N 10

int maximo(int valor[]);

int main() {

   int valor[N], cont,max;
   for (cont = 0; cont < N; cont++) {
     printf("Introduce el valor Nº%d: ", cont+1);
     scanf("%d", valor[cont]);
   }
   
   max = maximo(valor);
   printf("El máximo es %d\n",max);
   }

int maximo(int valor[]) {
  int max,cont = 0;
    max = valor[0];
   
  for (cont = 0; cont < N; cont++) {
    if (max < valor[cont]) {
      max = valor[cont];
    }
  }
  return max;
}
El scanf necesita referencias

scanf("%d", &valor[cont]);
Pues sí, era eso, que lo tenía con punteros y al pasarlo me lo he dejado...

Muchas gracias a todos ;)


Bueno... y ya tengo otro problemilla, aunque es más de concepto que de código xD

Estoy haciendo un programa que cuando le pones, por ejemplo:
    char diagrama[N][N]={
      {' ',' ',' ',' ',' ',' ',' ',' ',' '},
      {' ',' ',' ',' ',' ',' ',' ',' ',' '},
      {'*','*',' ',' ',' ',' ',' ',' ',' '},
      {'*','*',' ',' ',' ',' ',' ',' ',' '},
      {'*','*',' ',' ',' ',' ',' ',' ',' '},
      {'*','*',' ','*','*',' ',' ',' ',' '},
      {'*','*',' ','*','*',' ',' ',' ',' '},
      {'*','*',' ','*','*',' ','*','*',' '},
      {'*','*',' ','*','*',' ','*','*',' '}
};


Detecta que hay un diagrama de barras de abajo a arriba y que el carácter es *, después te dice que el grosor es 2 y los números son 7, 3 y 2.

Pues bien, en mi programa ya he hecho que me detecte el carácter y la inclinación, y ya tengo alguna idea para hacer que empieze a leer para detectar el grosor y demás, pero al ponerme a hacerlo, necesito una posición inicial, la cosa es que si hay alguna manera de hacer una función "fija" que abarque todas las posibilidades, porque yo he pensado en hacerlo tipo:

if (inclinación abajo arriba)
ini=N-1, inj=0, inj++ /código leer/
else
if (inclinación arriba abajo)
ini=N-1; j=N-1 ;j-- /código leer one more time/
else (bla bla bla...)

En resumen, hacer la función entera para cada posibilidad, no sé si es muy descabellado, me imagino que sí... hay alguna forma de hacerlo más eficiente?
Lo del programa de antes, lo he probado y funcionaba bien. Lo único que el compilador te daba un warning, pero nada grave xD

Con lo del diagrama de barras, es que no se lo que es xDD
gracias por la ayuda inverson88 ya me funciona pero me puedes explicar esto de el (float)(y2-y1)/(x2-x1) porque se pone el float antes de la operacionesto no lo abia visto yo, siempre declaraba una variable de tipo float y luego la usaba pero sin poner el float antes de usarla y me funcionaba si me lo puedes decir gracias. ein? [oki] [ok]
Yo llevo poco programando, pero creo que se pone (float) delante de la operación para que evalúe el resultado de la operación entre 2 int como un float, por ejemplo, si yo tengo:

int x=3,y=2;
float resultado;

resultado = x/y <-- Creo que devolvería 1 (no estoy seguro)

En cambio, poniendo resultado = (float)x/(float)y devuelve 1.5


Por cierto, para mi problema, ya tengo el código prácticamente acabado y funciona, pero claro, en plan chustero, si alguien me quiere/puede ayudar a simplificarlo u optimizarlo que me lo diga por aquí y le mando el código por MP para que veáis exactamente lo que me están pidiendo y ya lo discutimos por allí, ya que se trata de una entrega y podría venir algún avispado de la clase por aquí, que no sería extraño que se pasaran por EOL ^^" (llamadme desconfiado xD)
por ejemplo:

int x=3,y=2;
float resultado=0; //Inicializamos a 0 para que no guarde "basura"

resultado=(float)x/y;

Serginius con ponerlo como he indicado vale, no hace falta (float)x/(float)y;

Tenemos dos variables ("x" e "y") que guardan dos enteros. Una operación que implique como resultado otro tipo de variable (long int o float) te va a devolver un resultado no satisfactorio, para convertir una operacion de enteros a real lo indicamos en almenos uno de las variables implicadas.
Espero que se me haya entendio jaja que creo que no me expresao bien :P
Os voy a subir en unos minutos unos "boletines" de ejercicios que nos han mandado en el instituto cuando hemos estado dando C. Voy a bajarlos y os lo subo a megaupload ;)

PD: http://www.megaupload.com/?d=BBH6BQXZ

Si quereis material de Java yo estoy empezando (tanto ejercicios como explicaciones y tal) me lo deciis y voi subiendo cosillas :P
Un par de notas.
Serginius escribió:
Puyover escribió:Una duda que me ha surgido. Porque reservas así la memoria para el puntero?
No podrías haber hecho:
int *p, int array[N], cont;
p = &array[0];

?
Aunque supongo que lo tuyo será mas eficiente, no lo se :p

Yo tampoco lo sé xD Lo he hecho así porque es como salía en un ejemplo de punteros que nos han puesto.


Ambos métodos de asignación de memoria son equivalentes en funcionamiento, siempre que se use malloc con precaución. La principal diferencia es que malloc asigna memoria dinámicamente; en ocasiones no podrás crearte arrays de x valores hasta un cierto momento dado, en el que conozcas el valor de x por ejemplo.

Una cosilla. Las líneas
p = &array[0];

y

p = array;

son equivalentes.

Serginius escribió:Yo llevo poco programando, pero creo que se pone (float) delante de la operación para que evalúe el resultado de la operación entre 2 int como un float, por ejemplo, si yo tengo:

int x=3,y=2;
float resultado;

resultado = x/y <-- Creo que devolvería 1 (no estoy seguro)

En cambio, poniendo resultado = (float)x/(float)y devuelve 1.5


Esto me da hao mil quebraderos de cabeza. Es muy importante tener en cuenta los castings entre diferentes tipos de datos. Voy a seguir con el ejemplo que ha puesto Serginius, y a poner varias configuraciones para intentar aclarar las cosas.

float resultado;
int x = 3;
int y = 2;
resultado = x /y;

El procesador divide 3 / 2, y como x e y son enteros, solo toma la parte entera del resultado; es decir, 3 / 2 = 1.5; int (1.5) = 1. Pero ese 1 hay que asignárselo a una variable de tipo float, por lo que ahora el 1 se pasa a formato float. Por lo tanto, resultado = 1.00. Todos los float tienen parte decimal.

resultado = (float) (x) / (float) (y);

Ahora sí se dividen dos floats, 3.00 / 2.00 = 1.50.

Iverson88 escribió:int x=3,y=2;
float resultado=0; //Inicializamos a 0 para que no guarde "basura"

resultado=(float)x/y;

Serginius con ponerlo como he indicado vale, no hace falta (float)x/(float)y;

Esto que dices es válido en ciertas arquitecturas... pero no es una verdad universal. Lo que estás haciendo es forzar a x a ser float, pero no se dice nada acerca de y, y el encargado de hacer los casts (no sé si será el compilador) puede hacer todo al revés de lo que piensas.

Iverson88 escribió:Una operación que implique como resultado otro tipo de variable (long int o float) te va a devolver un resultado no satisfactorio, para convertir una operacion de enteros a real lo indicamos en almenos uno de las variables implicadas.
Espero que se me haya entendio jaja que creo que no me expresao bien


Suena borde (sorry), pero más peligroso es hacer una operación entre dos operadores de distinto tipo. Dividir un float con un int te va a dar resultados imprevisibles, según la arquitectura en la que trabajes. En VS2005 por ejemplo, tu resultado me habría dado 1.00 (estuve un par de días buscando un fallo tan tontaco como ese). En linux, sin embargo, sale 1.5. Igual era porque en VS2005 programaba en C++... pero también puede que si hubiese programado en C me hubiese dado el mismo problema.

Siempre siempre siempre hay que hacer cast en TODOS los operandos, cuando la variable en la que vas a guardar el resultado es de otro tipo. Así te ahorras quebraderos de cabeza.

Una muy buena guía de referencia es "Aprenda ANSI C como si estuviera en primero". Muy currada y todo queda bastante claro.
Esto que dices es válido en ciertas arquitecturas... pero no es una verdad universal. Lo que estás haciendo es forzar a x a ser float, pero no se dice nada acerca de y, y el encargado de hacer los casts (no sé si será el compilador) puede hacer todo al revés de lo que piensas.


Ehm.... es una verdad tan universal como el estándar y no tiene NADA que ver con la arquitectura.

Saludos.
Tan estándar como que en Linux y en Windows se producen resultados distintos?
Srpatato yo hablo desde mi experiencia, windows + dev-c++ y x86 ni más ni menos
Ooook. No sé, creí relevante decir eso, porque pueden suceder errores raros y tal.

Asunto zanjado, que cada uno programe como le salga de los buebos XD
srpatato escribió:Tan estándar como que en Linux y en Windows se producen resultados distintos?


No se trata de Linux / Windows. Se trata del compilador. De todos modos, me parecería muy raro que algún compilador malinterpretara esa parte del estándar porque es bastante básica para muchos aspectos del propio lenguaje.

Saludos.
@srpatato gracias por el apunte de los punteros [oki]

Entonces se supone que si usas gcc, tanto en Linux como en Windows la linea:

resultado=(float)x/y;

produce resultados correctos no?
A mi lo del (float)x/(float)y me lo puso el profe en un código mio al verlo, no sé, yo lo pondría, que total no viene de 4 letras xD
Serginius escribió:A mi lo del (float)x/(float)y me lo puso el profe en un código mio al verlo, no sé, yo lo pondría, que total no viene de 4 letras xD
creo que ponerle float a cada variable en vez de a la operacion es mas una mania que un necesidad para obtener un valor real de una division de dos enteros
La cosa es algo más o menos así: Cuando se hace una operación aritmética se busca un tipo aritmético común y ambos valores se promocionan a ese tipo. Se hace la operación y se asigna el resultado haciendo las conversiones pertinentes.

Es interesante ver que en 'a = b <op> c' el tipo común puede no ser ni el de a ni el de b ni el de c.

Saludos.
Ahí está, no me salía lo que dice Ferdy. El tema es que yo creía recordar que la promoción se hacía hacia el tipo que contiene menor información (int), en lugar de al de mayor información (float). Pero con lo que habéis dicho, ya no me queda claro cuál es el modo de promoción y seguramente esté equivocado.

En cualquier caso, y esto ya es personal, NO poner (float) x / (float) y EMHO es una chapuza. En este caso solo mezclas dos operandos de tipo int, pero cuando programes algo más tocho y tengas que hacer chorizos de cuentas, a no ser que vayas haciendo cuentas parciales, te puedes hacer la picha un lío.
Ahí está, no me salía lo que dice Ferdy. El tema es que yo creía recordar que la promoción se hacía hacia el tipo que contiene menor información (int), en lugar de al de mayor información (float). Pero con lo que habéis dicho, ya no me queda claro cuál es el modo de promoción y seguramente esté equivocado.


Piensa en el siguiente caso:

unsigned long a;
...
unsigned long b = a + 1;


Según el estándar, 6.4.4.1 punto 5 ese '1' es de tipo 'int'. Si conviertes todo a 'int'...

Como ves no tiene mucho sentido el modelo que planteas.

En cualquier caso, y esto ya es personal, NO poner (float) x / (float) y EMHO es una chapuza. En este caso solo mezclas dos operandos de tipo int, pero cuando programes algo más tocho y tengas que hacer chorizos de cuentas, a no ser que vayas haciendo cuentas parciales, te puedes hacer la picha un lío.


Generalmente no es normal tener fórmulas muy grandes con tipos de datos enteros y esperar datos en coma flotante.

Por otro lado, hacer casting a float puede no ser tan interesante si x e y no son 'int'.

Saludos.
¿Dónde se puede ver el estándar, y ese punto en concreto?
Ahem, http://www.open-std.org/JTC1/SC22/WG14/ ... .html#9899

En concreto ese punto dice: "The type of an integer constant is the first of the corresponding list in which its value can
be represented." y la lista para 'Decimal Constant' es "int, long int, long long int".
Ferdy escribió:Ahem, http://www.open-std.org/JTC1/SC22/WG14/ ... .html#9899

En concreto ese punto dice: "The type of an integer constant is the first of the corresponding list in which its value can
be represented." y la lista para 'Decimal Constant' es "int, long int, long long int".


Gracias por el enlace.

He mirado el documento más reciente de esa web, pero en el punto 6.4.4.1 al que te referías lo que se explica no son las promociones, sino el tipo y la base numérica de las constantes, no tiene nada que ver con la promoción.

Lo que dice esa frase es: mírame el número entero con el que estás operando, y asígnamelo al tipo en el que quepa dicho dato.
Es decir, el número 24 se asigna en un int, puesto que cabe en un int.
El número 54353534534543, que no cabe en un int, se asigna a un long int.
Y un número que no quepa en ninguno de los dos tipos anteriores se asigna a un long long int.

El casting de variables viene en el punto 6.3, y más concretamente en el punto 6.3.1.8.1. En efecto, la tercera condición es: si uno de los dos operandos es un float (y ninguno de los operandos es double ni long double), el otro se promociona a float y se operan ambos como si fueran float.

Más o menos (no me lo he leído a fondo) parece que, en caso de dos operandos de distinto tipo, se opera en aquél que contenga más información (o tenga mejor ranking, como dicen en ese documento). Así pues, yo estaba equivocado (pero eso sí, sigo recomendando especificar la promoción o la democión (?) siempre que haga falta, a cabezón no me gana nadie :P)
Interesante el documento este. No lo conocía xD
Supongo que java que fue influido por C seguirá el mismo estándar, aunque claro sin tipos como long double, etc o me equivoco?
vamos resumiendo... Que como lo puse yo es lo suyo no? XD
MMM sí en general, pero no para mi cabezonería XD
srpatato escribió:He mirado el documento más reciente de esa web, pero en el punto 6.4.4.1 al que te referías lo que se explica no son las promociones, sino el tipo y la base numérica de las constantes, no tiene nada que ver con la promoción.


Es que yo no dije que hablara de las promociones. Intentaba ilustrar por qué el modelo de promociones que planteabas era ridículo. En esa suma estarías operando en 'int' (por culpa del 1) cuando deberías operar en unsigned long (por tener más rango).

pero eso sí, sigo recomendando especificar la promoción o la democión (?) siempre que haga falta, a cabezón no me gana nadie


Es que cuando haga falta si no lo haces, no funciona :P

- ferdy
Ferdy escribió:
srpatato escribió:(...)


Es que yo no dije que hablara de las promociones. Intentaba ilustrar por qué el modelo de promociones que planteabas era ridículo. En esa suma estarías operando en 'int' (por culpa del 1) cuando deberías operar en unsigned long (por tener más rango).

Bueno, creía que hablabas de lo mismo, puesto que hilabas todo muy correctamente en ese post XD

Ferdy escribió:
srpatato escribió:pero eso sí, sigo recomendando especificar la promoción o la democión (?) siempre que haga falta, a cabezón no me gana nadie


Es que cuando haga falta si no lo haces, no funciona :P

- ferdy


En esto estamos de acuerdo XD. Yo, al menos, siempre especificaré el tipo de cast que quiero usar cuando los operandos son de distinto tipo que el resultado, haga falta o no.
Buenas, tengo otra duda!

Cómo puedo hacer que me redondee hacia arriba el resultado de una operación? (En C), me iría de perlas para un programa pero no se hacerlo... algo similar a cuando haces la división entre 2 ints, que redondea hacia abajo, pues eso...

Gracias!
Serginius escribió:Buenas, tengo otra duda!

Cómo puedo hacer que me redondee hacia arriba el resultado de una operación? (En C), me iría de perlas para un programa pero no se hacerlo... algo similar a cuando haces la división entre 2 ints, que redondea hacia abajo, pues eso...

Gracias!

Si son 2 enteros, al hacer la división entera sumale 1 ^^.

Si es para redondear otras operaciones, usa ceil, o haz un cast a int y suma 1.

Y es distinto truncar que redondear hacia abajo, solo son lo mismo para positivos.
140 respuestas
1, 2, 3