Menú

Mostrar Mensajes

Esta sección te permite ver todos los mensajes escritos por este usuario. Ten en cuenta que sólo puedes ver los mensajes escritos en zonas a las que tienes acceso en este momento.

Mostrar Mensajes Menú

Mensajes - Serapis

#3111
Sí, has creado una clase servidor, y una sola instancia, pero... ...esa y solo esa instancia es la que debe ser visible a todos. Ninguna otra instancia de esa clase.
Para que eso sea posible, debe crearse una única instancia, no importa cuantas veces se pretenda crear instancias de clase.

Y el modo de lograr esto, es crearla ya tu y guardarla... y quien solicite una instancia (no debe poder crearse desde fuera delservidor), tu le entregas una referencia.

Así todos tienen exactamente la misma instancia, porque siempre entregas la referencia a la única clase creada...


Para asegurarte que lo haces bien, debes hacer alguna prueba, como la que te sugerí aquí:
Cita de: NEBIRE en 15 Septiembre 2017, 21:28 PM
Un modo de probar que es correcto, es hacer lo siguiente.

Crear un método de prueba en el servidor:

Clase Server
   Entero p_Numero

   Funcion Nueva // Instancia
       p_Numero = NumeroAlAzar(entre 1millon y 10millones)     //crea un número al azar
   Fin funcion

   Entero = Funcion Probar
       Devolver p_Numero
   Fin funcion
Fin clase


Ahora para probar si son la misma instancia cuando se crea un cliente y se comunica con el servidor, luego invoca su método Probar:
Clase Cliente  
   // .... ya tiene sus métodos, esto es un añadido al método conectar...
   
   Buleano = Funcion Conectar(x,y,z)
      Servidor = Proveedor.IniciarServidor
      Mensaje Servidor.Probar  // <------------------------ Aquí probando el servidor...
      Devolver Existe(Servidor)
  Fin Funcion
 
Fin clase

Si existe una única instancia dle servidor, el número de la prueba debe ser siempre el mismo hasta que se destruya el servidor.
Si el servidor fue creado y luego cada cliente ofrece distintos números de prueba, es que se están creando instancias exclusivas para cada cliente...
#3112
Hay algunos lenguajes que sí permiten hacer esa evaluación, por ejemplo VBScript, tienen un método Eval(string), que puede (intentar) procesar un texto entrado por el usuario... Esto es posible, porque va interpretando, no requiere compilación...

Como casi ningún lenguaje posee esa funcionalidad, en efecto tienes que hacer como te dice Engel, sin necesidad de ir tan lejos, te basta 'crear tu pequeño lenguaje', es suficiente con dos expresiones ( te recomiendo ojear la "notación BNF", te dará las ideas necesarias para poder encajarlo todo de una forma sencilla y asimilable):
------> variable Operador variable
----------------> Operador variable

Te defino todas las producciones mínimas que podría requerir 'tu lenguaje':
-------------------------------------------------------------------------------
1 expresion = numero + spc + operador1 + spc + numero | operador2 + spc + numero
2 numero = 0-9 + [numero]
3 spc = espacio + [spc] |tabulador + [spc]
4 operador1 = " + "|" - "|" * "|" / "|" ^ "|" sqr "|" or "|" and "|" xor "|" mod "
5 operador2 = " not "|" sin "|" cos "|" round "|" int "
======================================

- El simbolo "+" indica que concatenación de producciones (de partes, que tras una parte va obligadamente (salvo que sea opcional) otra parte).
- Los símbolos opcionales, tenemos 3:
------->  "x|y|z" indican que se elige uno solo entre los posibles elementos delimitados por los separadores.
------->  "-" es un separador de un rango, por ejemplo A-E, equivale a: A,B,C,D,E,F
-------> "," es un separador de lista, por ejemplo: "Set", "Get", "Do"
- Los símbolos "[x,y,z] indican que el contenido interior entre corchetes es opcional.
- Los literales (que en la expresión deben escribirse tal cual), en la descripción van encerrados entre comillas (para distinguirlos de otra producción).
    Ojo los símbolos "" + "", "" - "", (en operador1) son literales.


Llevándolo un poco más lejos puede hacerse algo más complejo, aparte de añadir más operadores (que es trivial), puedes añadir la admisión de números no solo en la base decimal y enteros, tambien  binario, hexadecimal, octal, etc... ...y/o decimales (coma flotante)
Admitiendo más posibilidades con los números
----------------------------------------------------------------------
2 numero = numeroDec | numeroBin | numeroHex | numeroOct  // sobrescribimos lo que es un número.
6 digitoBin = 0|1
7 digitoOct = digitoBin | [2-7]
8 digitoDec = digitoOct | [8-9]
9 digitoHex = digitoDec | [A-F]

10 digitosBin = digitoBin + [digitosBin]
11 digitosOct = digitoOct + [digitosOct]
12 digitosDec = digitoDec + [digitosDec]
13 digitosHex = digitoHex + [digitosHex]

16 numeroBin = "Bx" + digitosBin
17 numeroOct = "Ox" + digitosOct
18 numeroDec = digitosDec
19 numeroHex = "Hx" + digitosHex
Los números con decimales, lo dejo a tu esfuerzo...

Y por supuesto admitir variables, además de números...
-------------------------------------------------------------------------
0 valor = variable | numero
1 expresion = valor + spc + operador1 + spc + valor | operador2 + spc + valor // esta producción se modifica
14 variable = identificador + " = " + expresion
15 identificador = A-Z + [identificador] | A-Z + [0-9] + [identificador]
#3113
A ver Cristina Gusigusa...

De entrada, no entiendo bien por qué pides dos veces la cantidad de números que se deben generar al azar...
   
Citarprintf("¿Cuantos numeros quieres que te genere?:   ");
   scanf("%d",&x);
   printf("¿Cuantos numeros quieres que te genere?:   ");
   scanf("%d",&p);

Luego parece que el array 'a', tendrá el tamaño que el usuario da a 'x', pero el array 'b' tendrá el tamaño dado a 'p'... 'x' y 'p', va a ser que no sean el mismo valor (salvo que tu misma seas quien lo introduce o rara casualidad...
Entonces si los arrays no van a ser del mismo tamaño y especialmente si no hay garantías de que el array 'b' sea mayor que el array 'a', acabará dando un error en la línea 53
b[i]=a[i];
Que además, no veo que se vuelva a usar el array 'b' en parte alguna... Luego elimina el array 'b', elimina la petición de 'p', y si no quieres eliminar 'p, al menos haz: p == x

La indentación aparece confusa, y no queda claro (de un simple vistazo), que queda dentro de qué... sin un esfuerzo extra revisando llaves (que obvio hacer)...
El ordenamiento inverso es redunndante, una vez hecho de mayor a menor o de menor a mayor, el inverso, basta con recorrer el array desde el final hacia atrás, hasta llegar a 0.

Así el código queda resumido así para menor.dat
final = x-1
Bucle para i desde final hasta 0 retrocediendo
   GuardarAfichero a(i)
fin bucle

De hecho si se abren dos canales de escritura, pueden guardarse a fichero los dos al mismo tiempo (en el mismo bucle)


Abrir Fichero 1
Abrir Fichero 2
Bucle para i desde 0 hasta x-1
   GuardarAfichero 1 a(i)   //guardando fichero mayor.dat
   GuardarAFichero 2 a(x-i) //guardando al fichero menor.dat
fin bucle
Cerrar fichero 1
Cerrar fichero 2


Aunque para ordenar usas un algoritmo de burbuja... que son muy lentos, pero para ejemplos son perfectamente válidos...

Finalmente llegamos a la parte de contar las frecuencias...
De entrada, date cuenta que si el array ya está ordenado es superfluo recorrer todo el array, las veces que un valor aparezca, estarán contiguos... ...porque el array está ordenado. Como no sabemos cuantos valores distintos hay, usaremos un bucle indefinido (Mientras... condición...repetir)


Abrir fichero
i = 0
Hacer Mientras (i<(x-1))
  v = a(i)    //valor actual para el que vamos a contar sus apariciones (absolutas).
  f = 0 // contador de apariciones [s]frecuencia[/s]
  Hacer // OJO: Este bucle tiene la condición al final,
           // esto implica que como mínimo se entra SIEMPRE una vez al bucle.
     f += 1
     i += 1
  Repetir mientras (v = a(i) )
  GuardarAFichero v, f //guardamos el valor y las veces que salió dicho valor (esto a tu gusto y necesidad)

Repetir

Si (v <> a(i)) luego  // si el último valor (en el array) no estaba repetido, el bucle no lo pilla, se hace aquí (modificar el bucle para hacerlo, hacer perder erficacia en cada cilo, algo que solo podrá ocurrir una vez en el array, asi es más óptimo dejarlo fuera (hacer esta comprobación), tras el bucle.
    GuardarAFichero a(i), 1
Fin si

Cerrar Fichero


Finalmente una aclaración... aquí se están contando el número de apariciones de cada valor, no la frecuencia. La frecuencia en realidad sería dividir el tamaño del array entre la cantidad de apariciones de cada valor... yendo más lejor se podría luego  dar en porcentaje. (con luego, no quiero decir en otro bucle si no modificarlo en otro momento).

Ojo, que como para Rand, no pones límites... si alguien pide pongamos 20 números es fácil que no se repita ninguna vez... acota Rand a un rango de valores, por ejemplo entre 100 y 110 y que la cantidad de números a generar sea (obligatorio) por lo menos el doble o el triple de lo que es el rango, para que haya 'repes'...
...es decir si 'x' (que introduce el usuario) es menor que el rango entre MinVal y MaxVal, repite la petición... MinVal y MaxVal serían los límites menor y mayor entre los que elegir al azar...
#3114
mmmm... el casoes que la tipografía ideal para el programador... para cada programador... ya existe... su propia caligrafía, no existe ninguna mejor.
#3115
Veo que quedó desierta la propuesta... lástima.

Aunque el tiempo libre escasea, siempre se puede hacer algo.
#3116
Al margen de que sea cierto o falso, lo que es seguro es que si desconfías de tu guardaespaldas, cambies de guardaespaldas... Así que me parece correcto.
#3117
Vaya, deconocía lo de "modo "Siempre encendido".", esto supone en la práctica que habrá que evitar que nadie con estos móviles se 'arrime' a tí (o tu a ellos)...

Francamente no existe ninguna necesidad de esta ¿'tecnología'?. No hay mercado para ello, salvo la propia del espionaje.

No ofrece seguridad que no ofrezcan sistemas no basados en sistemas biométricos. Además que pasa si un amigo o familiar te pide que le dejes el móvil durante x tiempo, que el suyo se le ha estropeado y tiene que hacer y recibir llamadas muy urgentes???. Tendrá varias activaciones?. Serán activaciones limitadas?. Habrá una 'supercuenta' del 'owner'?. Si te dejas barba ya no te reconoce?. Y si estás a medio afeitar y recibes una llamada, no podrás contestar hasta que te afeites del todo, o te limpies la espuma?. Y si en un evento deportivo, caes al suelo y te arañas la cara y te sale una costra, todavía te reconocerá?. Y si en vez de barba te dejas bigote ?, y si es tipo Dalí?. Y si te hechas un rapado al 0, o te dejas una melena o unas rastas, te seguira´reconociendo?. y si te pones moreno o gamba por tomar el sol?. Y si te tiznas la cara para hacer de rey Baltasar (mientras hagas de rey Baltasar, no podrás usar el móvil) ?....
Y si te graban un vídeo de tu cara y se lo ponen luego a la cámara, te reconocerá, sabrá distinguir la realidad de un vídeo (un bebé de apenas unos meses sabe distinguir la diferencia)?

Apple, ya no sabe que hacer, quieren dar la nota y para ello cualquier cosa, aunque sea una payasada, les vale... El caos es que hay infinidad de cosas que pueden mejorar, en vez de perderse en tonterías...
#3118
jajajajaja... menudo jaleo se puede montar...

"Siri, aquí Tango, Lima, Delta, Delta, November..."

"Ejecutando acción: Torpedos listos y disparados, dirección norte..."
#3119
Efectivamente, como te dice AlbertoBSD, sin código, no se puede decir mucho, es jugar a adivinar...

Sin embargo normalmente cuando todo funciona y esto falla, lo que suele suceder (con bastante frecuencia), es que el servidor crea una instancia y el cliente llama a otra instancia de la clase servidor...

La solución es que exista una y solo una clase servidor...

Un poco de pseudocódigo te ayudará a entender el problema y facilitar la solución (dado el caso que éste sea el problema).

Clase Cliente
  Server Servidor

  Buleano = Funcion Conectar(x,y,z)  //x,y,z son posibles parámetros necesarios para la conexión, aquí se omite por claridad...
      Servidor = nueve Server //x,y,z
  Fin Funcion

  // Otros métodos de la clase...
Fin Clase

Como se ve, aquí se crea una instancia dle servidor... una instancia nueva, a la que se le asigna un espacio de memoria... y cada cliente... creará una instancia distinta, habrá tantas instancias distintas del servidor como clientes lo llamen.


Solución: Crear una clase y método estático... que contenga el servidor.
Así se crea una única instancia para todos los que llamen. La clase servidor, no puede ser creada desde fuera, pero puede ser instanciada, y exclusivamente invocando este método... La clase 'server' es pública pero 'no creatable', así esta clase crea una única instancia del servidor y sirve por tanto siempre la misma instancia a todos los clientes...

Clase estatica ProveedorServer
   Server p_Servidor  privado

   Server = Funcion IniciarServidor
       Si (p_Servidor no existe) luego    
           p_Servidor = Nuevo Server
       Fin si

       Devolver p_Servidor
   Fin funcion
   
   // Otros métodos que fueren necesarios para la clase...
Fin clase


que sería llamado así:
Clase Cliente
  Server Servidor
  ProveedorServer Proveedor

  Funcion Nueva //instancia
      Proveedor = Nuevo ProveedorServer
  Fin funcino

  Buleano = Funcion Conectar(x,y,z)  //x,y,z son posibles parámetros necesarios para la conexión, aquí se omite por claridad...
      Servidor = Proveedor.IniciarServidor //x,y,z
      Devolver Existe(Servidor)  //Existe: Comprueba que es una instancia válida de objeto.
  Fin Funcion

  // Otros métodos de la clase...
Fin Clase


Un modo de probar que es correcto, es hacer lo siguiente.

Crear un método de prueba en el servidor:

Clase Server
   Entero p_Numero

   Funcion Nueva // Instancia
       p_Numero = NumeroAlAzar(entre 1millon y 10millones)     //crea un número al azar
   Fin funcion

   Entero = Funcion Probar
       Devolver p_Numero
   Fin funcion
Fin clase


Ahora para probar si son la misma instancia cuando se crea un cliente y se comunica con el servidor, luego invoca su método Probar:
Clase Cliente  
   // .... ya tiene sus métodos, esto es un añadido al método conectar...
   
   Buleano = Funcion Conectar(x,y,z)
      Servidor = Proveedor.IniciarServidor
      Mensaje Servidor.Probar  // <------------------------ Aquí probando el servidor...
      Devolver Existe(Servidor)
  Fin Funcion
 
Fin clase

Si existe una única instancia dle servidor, el número de la prueba debe ser siempre el mismo hasta que se destruya el servidor.
Si el servidor fue creado y luego cada cliente ofrece distintos números de prueba, es que se están creando instancias exclusivas para cada cliente...
#3120
Java / Re: Intercesión o cruce de 2 polígonos
14 Septiembre 2017, 18:23 PM
No he mirado el código, creo que si te lo han facilitado y te dicen que funciona, tu mismo debes verificar si es verdad que funciona o no...

Veamos... un polígono es un área encerrada sobre líneas rectas... a pruimera impresión, un polígono, puede considerarse como un punto grande, pero que tiene 'varios centros'.

Si sabes detectar la colisión de dos rectángulos, la segunda operación es tratar de verificar esto. Es decir si el área que ocupa un polígono no está 'encima' de otro, no merece la pena perder tiempo en comprobar más.

O dicho de otro modo, al caso conviene 'cuadrar' el polígono, obteniendo 4 puntos, los puntos más lejanos en las 4 orientaciones, o dicho de modo simple, encerrar el polígono en un rectángulo.

Si la comparación de esos rectángulos, no se intersectan, no vamos más allá y solo cuando sí, es cuando vale el gasto de tiempo en verificar en profundidad la colision entre polígonos.

A grandes rasgos en pseudocódigo:

1 - Cuando se crean los polígonos o cuando se modifica su tamaño o forma, se calcula el rectángulo que lo encierra (es decir, esto no debe calcularse cada vez que se quiera determinar una colisión, es redundante... se calcula una sola vez y se mantiene mientras no cambie). Esto se hace por cada polígono para el que deba ser verifcada una colisión:


Estructura Rectangulo
   Izquierda
   Superior
   Derecha
   Inferior
Fin Estructura

// Dados los puntos de un polígono, devuelve el rectángulo en el que encaja (ojo, con la posición actual)
Rectangulo = Funcion EncerrarPoligonoEnRectangulo(Punto Puntos)
   Rectangulo r, Punto p
   // el primer punto asume los límites iniciales, que serán actualizados por el que los supere.
   r.Izquierda = p(0).X
   r.Superior = p(0).Y
   r.Derecha = p(0).X
   r.Inferior = p(0).Y

   Por cada p en Puntos
       Si (p.X < r.Izquierda) luego
           r.Izquierda = p.x
       Sino
           Si (p.X > r.Derecha) luego
               r.Derecha = p.X
           Fin si
       Fin si

       Si (p.Y < r.Superior) luego
           r.Superior = p.Y
       Sino
           Si (p.Y > r.Inferior) luego
               r.Inferior = p.Y
           Fin si
       Fin si
   Siguiente

   // OJO: antes d ehacer la devolución lo movemos al origen, para evitar restas en lo sucesivo, solo sumas.
   Devolver MoverRectanguloAOrigen(r)
Fin funcion

// Desplaza el rectángulo al origen (la esquina superior izquierda se posiciona en el eje de cordenadas)
// NOTA: que esto equivale a poner las medidas del rectangulo (mide.Ancho, Mide.Alto) y posición (x = 0, y = 0)
Rectangulo = Funcion MoverRectanguloAOrigen(Rectangulo r)
    r.Derecha = r.Derecha - r.Izquierda
    r.Izquierda = 0

    r.Inferior = r.Inferior - r.Superior
    r.Superior = 0

    Devolver r
Fin funcion

// Otra función para desplazar adonde sea (desde el origen)...
Rectangulo = Funcion MoverRectanguloDesdePosOrigen(Rectangulo r, Posicion p)
   r.Izquierda =p.X
   r.Derecha = (r.Derecha + p.X)

   r.Superior = p.Y
   r.Inferior = (r.Inferior + p.Y)

   Devolver r
Fin funcion

// Otra función para desplazar adonde sea (desde donde está ahora)...
Rectangulo = Funcion MoverRectanguloDesdePosActual(Rectangulo r, Posicion p)
   r.Izquierda = (r.Izquierda + p.X)
   r.Derecha = (r.Derecha + p.X)

   r.Superior = (r.Superior + p.Y)
   r.Inferior = (r.Inferior + p.Y)

   Devolver r
Fin funcion


...ahora tengo que salir, continúo a la noche, más bien de madrugada...