[ Foro de Pascal ]

problemas de como enfocar la multiplicacion de dos strings de numeros.

21-May-2010 13:05
sergio cienfuegos caldevilla
10 Respuestas

hola nuevamente a todos los profes. ya tardaba en trabarme otra vez. tengo problemas de como enfocar el problema de multiplicar dos cadenas de numeros grandes(50 a 100 cifras), no se como enfocarlo. tambien en como contar las que se llevan dentro de la multiplicacion. cuando puedan si pueden hecharme una mano estare agradecido. esto es lo que tengo en el papel, ideas que me surgen pero no es nada firme.

program multcadena;
var
       numero1,numero2:string[50];  

function multi(a,b:string[50]):string[50];
   var
       cadena1,cadena2:string[50];
       n1,n2:integer;
       res_par:array[;
       lista1:array[n1..1] of real;
       lista2:array[n2..1] of real;
   begin
       cadena1:=lista1;
       cadena2:=lista2;
       n1:=length(cadena1);
       n2:=length(cadena2);
       for lista1:=n1 downto 1 do
           for lista2:=n2 downto 1 do
           lista1*lista2;
             if lista1[n1,1]*lista2[n2,1]

ante todo gracias por adelantado, saludos.


21-May-2010 14:12
sergio cienfuegos caldevilla

x cierto,esa funcion que hay arriba esta es el conjunto de ideas que me plantee, o formas de abordar el problema, se que no tiene sentido, solo puse ideas y pretendia desechar lo prescindible, pero mis conocimientos no me lo dan para plasmarlo. XD. saludos.


23-May-2010 16:45
Antonio P.G.

A ver, yo no soy profe, pero contesto a la pregunta. Antes un comentario: ese código no tiene ni pies ni cabeza.

"cadena1:=lista1" es una instrucción imposible. ¿Por qué? Porque las variables pertenecen a tipos de datos diferentes.

El problema yo lo enfocaría mejor de la siguiente forma:

- Leer (número1).
- Leer (número2).
- Multiplicar (número1, número2, resultado)
- Mostrar_resultado (resultado).

La cosa es que el array del resultado debe tener una mayor dimensión que los arrays de los factores número1 y número 2. Yo diría que el tipo de datos de los elementos de los arrays debería ser un tipo subrango "0..9". Es mejor trabajar con números que con caractéres, creo yo.

Por cierto, aquí las operaciones "mod" y "div" pueden ser útiles.

Leer y escribir un array no es muy complicado, por lo que la mayor complejidad se la lleva el algoritmo de "Multiplicar". Aquí uno se las tiene que apañar para que salga bien. Yo tendría en cuenta que, por ejemplo:

  350
 X 25
------
 1750
+ 7000
------
 8750

En fin, eso es todo. Espero haber sido de ayuda.
Hasta luego.


24-May-2010 01:44
sergio cienfuegos caldevilla

es que el ejercicio dice literalmente esto:
'Crear un programita que multiplique dos números "grandes", de entre 30 y 100 cifras, por ejemplo. Para esos números no nos basta con los tipos numéricos que incorpora Pascal, sino que deberemos leerlos como "string" y pensar cómo multiplicar dos strings: ir cifra por cifra en cada uno de los factores y tener en cuenta lo que "me llevo"...

y la verdad es que lo que me explicas arriba creo que parte lo entiendo, pero no soy capaz de empezarlo, es como sabes los datos y haber estudiado la leccion, pero no sabes como utilizarlo para expresar lo que me piden, y al no tener ningun ejemplo de referecia para comparar y asimilar las formas, me veo incapaz.
si pudierais ser un poco mas explicitos, os lo agradeceria en el alma.
siento las molestias producida por mis preguntas y gracias por adelantado.

PD. por cierto gracias antonio por la respuesta anterior.
saludos, sergio.


24-May-2010 10:11
Antonio P.G.

Hola Sergio.

La cosa es que utilizando strings, lo que tienes son caracteres, y como bien sabes, los caracteres no se pueden sumar para producir resultados numéricos.

Por ello, te aconsejo que vayas por partes. Primero, crea un programa que lea un string de dígitos, (es decir, un número sin espacios entre las cifras), para devolver ese mismo número en pantalla, pero con un tipo de datos array. Es decir, un programa más o menos así:

variables
 cadena : tipo string;
 arreglo : tipo array [1..N] of 0..9;
comenzar
 leer un numero string (cadena);
 convertir numero string a array (cadena, arreglo);
 mostrar numero array (arreglo);
fin.

Te recuerdo que el tipo string es como un array de 256 caracteres que va desde 0 hasta 255. En la posición cero guarda la longitud del string, por lo que te interesa hacer la función "convertir" desde 1 hasta N, o hasta length(cadena).

De momento te recomendaría que empezases por ahí. Si aún así nada, dilo, ok?

Ciao!


26-May-2010 23:44
Nacho Cabanes (+31)

Tienes que pensar en los pasos que hacer para dar una multiplicación "a mano":

 123
x 134
------
 492
369
123
------
16482

Es decir, primero tomas la última cifra del número inferior, y la vas multiplicando por cada una de las cifras del número superor (y teniendo en cuenta si "te llevas algo" porque el resultado sea mayo que 10).

Los únicos dos "trucos" necesarios son extraer cada cifra de la cadena (con los corchetes) y saber su valor numérico (la función "ord" te dice su código ASCII, que es 48 para el "0", 49 para el "1" y así sucesivamente).

Visto así, puede parecer que necesitas guardar todos los resultados intermedios de la multiplicación, pero si lo piensas un poco te darás cuenta de que no, de que te basta con guardar un único valor acumulado...


28-May-2010 17:57
sergio cienfuegos caldevilla

hola profes, he estado trabajando mucho con lo que me dijisteis, aunque pienso que este ejercicio es bastante grueso para el material contenido en los temas que he avanzado. he investigado por mas paginas, he leido mucho, y llevo tres o cuatro dias dandole 6 horas diarias y me ha salido una funcion para pasar de string a array(que no se corregirla). si me hechais una mano orientadome hacia donde seguir os lo agradeceria. estas son las funciones hasta ahora.
program multcadena2;
var
       numero:string[50];

function convertir(a:string[50]):array[1..length(numero) of 0..9;
   type
       arreglo=integer;


   const
       cadena:string[50];
   var
       sub_arreglo:array[1..length(numero)] of arreglo;
       contador:integer;
   begin

       contador:=1;
       cadena:=a;
       readln(a);


       for a:=ord(a) to length(numero);
       begin
          for arreglo:=1 to length(numero);
          read(arreglo[contador]);
          contador:=contador+1;
          end;
       arreglo:=convertir;
       end;
un saludo, y gracias profes.
por cierto antonio, como sabes mucho mas que yo, tambien eres profe.. XD.


28-May-2010 23:53
Nacho Cabanes (+31)

No tengo muy claro lo que pretendes hacer...

- Por una parte, no necesitas una función que convierta todo un string a array de números, porque tu irás trabajando cifra a cifra.


- En la cabecera de "function" te falta cerrar el corchete del array: ]


- Según la versión de Pascal, quizá no puedas devolver un tipo de datos tan complejo y tengas que declararlo con type:

type
       filaCifras =  array[1..50] of 0..9;


- Aun así, quizá tampoco puedas devolver ese tipo de datos, según el compilador. Por ejemplo, con Turbo Pascal 5 tampoco compila si haces

function convertir(a:string): filaCifras;


- No entiendo por qué declaras el tipo "arreglo" como sinónimo de "integer".


- Declaras una variable "sub_arreglo" que no usas.


- No necesitas la variable "contador", si vas a usar otra variable "a", "i" o similar para controlar el "for".


- La variable "a" no la declaras, y además no puede servir a la vez para controlar un "for" (que suena a variable numérica) y para recibir el valor de "cadena" (o viceversa), porque cadena es un "string".


- No necesitas ningún "read", porque no lees nada desde teclado, sino desde otro array (un string es simplemente un tipo especial de array).


- El valor final de la función deberías devolverlo con una orden similar a "convertir := arreglo"  no "arreglo := convertir"


29-May-2010 13:23
Antonio P.G.

Vamos a ver Sergio.

Un par de cositas que te ha comentado Nacho:

1. Un string es como casi casi como un array de 256 caracteres. La cosa es que existen unas cuantas funciones creadas para los strings, es decir, funciones de concatenación, de copiar, de cortar,... La cosa es que deberías de elegir: o strings o arrays. ¿Por qué strings? Pues porque a la hora de introducir un número por el teclado, lo introduces de forma normal, como si fuese a mano. ¿Inconvenientes de los strings? Pues que son caracteres y no números lo que almacenan. ¿Por qué un array? Pues porque puedes almacenar los dígitos como números. ¿Inconvenientes? Que hay que introducirlos separados.

2. Las funciones en Pascal sólo pueden devolver (o deberían) tipos simples. Tipos simples son: boolean, byte, integer, word, longint, real,... (y alguno más que me estaré dejando). El resto, son tipos ESTRUCTURADOS. Los arrays, records,... esos son estructurados. La cosa es que un string, si no me equivoco, es un estructurado, pero TP7 te permite devolverlo como resultado de una función.
Nacho, tengo una duda, y es que no recuerdo si te permitía devolver un tipo enumerado. No me suena mucho, pero ahí está. Tampoco recuerdo si permitía devolver tipos de arrays :-/.

Creo de todas formas que estás intentando algo muy complicado para los conocimientos que tienes. Yo te recomendaría (como alumno que he sido y que aún soy, tanto de facultad como de Nacho), que hicieses más ejercicios de anteriores temas para mejorar tu base. En concreto, con respecto a los arrays, ejercicios tales como:

- Leer dos arrays de 10 números o letras y ver si son iguales.
- Leer un array y encontrar el mayor de los elementos.
- Leer dos arrays y decir cuál suma es mayor (sumando los números).

Y todo ello usando subprogramas. Tal vez me equivoque, y sepas más que eso, pero por si acaso lo comento.

Suerte.


29-May-2010 17:50
sergio cienfuegos caldevilla

la verdad es que creo que tengo conociemientos, por que estoy estudiando de 4 paginas distintas, para ver los diferentes enfoques. es decir, si yo cogiera el programas de multiplicar dos numeros de entre 30 y 50 cifras hecho, sabria leerlo, cual texto de un libro, y entenderia como se hace y todo. hasta ahora habia avanzado muy bien pero este ejercicio es demasiado grueso para el tema en el que esta. tambien hecho de menos que en este tutorial no haya mas ejercicios intermedios.
tambien tengo la duda de que el free pascal sea el mejor programa para esto.
mi cabeza tiene que ver algo resuelto, para entender el porque de las cosas, y despues saber aplicarlo, por eso los ejemplos son tan valiosos para mi, pero he buscado mucho por ahi, y no he encontrado ejemplos, aunque sean sencillos, de como abordar este programa.
por cierto gracias por vuestra paciencia conmigo, pero cuando arranque, y entienda la dinamica, sera otro cantar. saludos


30-May-2010 13:12
Nacho Cabanes (+31)

Me parece buena política lo de mirar 4 páginas distintas, porque cada persona tiene su forma de explicar y cada persona propone unos tipos de ejercicios. Cuantas más formas de explicar distintas leas, más fácil será que entiendas los conceptos, y cuantos más ejercicios hagas, mejor los asimilarás realmente.

Pero insisto en eso último: a programar no se aprende leyendo, sino programando. Así que la única forma de aprender "de verdad" es hacer cientos de ejercicios, no leerlos.

A modo de curiosidad: mi curso de Pascal tiene -para mi gusto- pocos ejercicios propuestos, porque es antiguo, de una época en la que los ejercicios yo los proponía en clase, no en los apuntes. Hoy en día explico de otra forma y cada vez incluyo más ejercicios incluso en los apuntes. Por ejemplo, en la introducción a C# hay 110 ejercicios resueltos, debe haber una cantidad algo superior de ejercicios propuestos y en clase hemos hecho 250 ejercicios en lo que va de curo.

En cuanto a este ejercicio concreto... es cierto que tiene un nivel de dificultad alto para esa parte del curso, pero SÍ se puede resolver con los conocimientos que se tienen en ese punto. No es trivial, así que hay que ser muy ordenado y tener las ideas claras, pero se puede resolver.

Aun así, te propongo un ejercicio alternativo, bastante similar (mucho más de lo que puede parecer a simple vista), pero más sencillo: un programa capaz de sumar dos números enteros de 30 cifras.






(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.)