Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   Varios (https://www.clubdelphi.com/foros/forumdisplay.php?f=11)
-   -   Problema con Numero a Letra - Muestra "Un Mil" en vez de "Mil" (https://www.clubdelphi.com/foros/showthread.php?t=85833)

Jovalca 13-05-2014 13:44:47

Problema con Numero a Letra - Muestra "Un Mil" en vez de "Mil"
 
Hola a todos.

Ante todo, gracias por vuestro tiempo en echar un vistazo a este código.
Tengo el siguiente código, que saqué de estos mismos foros para pasar un numero a letras, tipo 1.220 a "Mil doscientos veinte".
Todo va bien con casi todos los números, he probado un montón y parece que todo va bien, pero cuando pones 1000, el texto muestra "UN MIL" en vez de "MIL".
He intentado solucionarlo pero lo único que he conseguido es que después no muestre otros números.

El codigo es el siguiente:

Código Delphi [-]
Function TForm1.CantidadEnLetra(curCantidad: Currency; MonNal: integer): String;
 var i: integer;
     Cantidad, Centavos: Currency;
     BloqueCero, NumeroBloques, Digito: Byte;
     PrimerDigito, SegundoDigito, TercerDigito: Byte;
     Resultado, Temp, strCentavos, Bloque: String;
     Unidades: Array[0..28] of String;
     Decenas: Array[0..8] of String;
     Centenas: Array[0..8] of String;
begin

Unidades[0] := 'UN'; Unidades[1] := 'DOS'; Unidades[2] := 'TRES'; Unidades[3] := 'CUATRO';
Unidades[4] := 'CINCO'; Unidades[5] := 'SEIS'; Unidades[6] := 'SIETE'; Unidades[7] := 'OCHO';
Unidades[8] := 'NUEVE'; Unidades[9] := 'DIEZ'; Unidades[10] := 'ONCE'; Unidades[11] := 'DOCE';
Unidades[12] := 'TRECE'; Unidades[13] := 'CATORCE'; Unidades[14] := 'QUINCE'; Unidades[15] := 'DIESISEIS';
Unidades[16] := 'DIESISIETE'; Unidades[17] := 'DIESIOCHO'; Unidades[18] := 'DIESINUEVE';
Unidades[19] := 'VEINTE'; Unidades[20] := 'VEINTIUNO'; Unidades[21] := 'VEINTIDOS';
Unidades[22] := 'VEINTITRES'; Unidades[23] := 'VEINTICUATRO'; Unidades[24] := 'VEINTICINCO';
Unidades[25] := 'VEINTISEIS'; Unidades[26] := 'VEINTISIETE'; Unidades[27] := 'VEINTIOCHO'; Unidades[28] := 'VEINTINUEVE';

Decenas[0] := 'DIEZ'; Decenas[1] := 'VEINTE'; Decenas[2] := 'TREINTA'; Decenas[3] := 'CUARENTA';
Decenas[4] := 'CINCUENTA'; Decenas[5] := 'SESENTA'; Decenas[6] := 'SETENTA'; Decenas[7] := 'OCHENTA'; Decenas[8] := 'NOVENTA';

Centenas[0] := 'CIENTO'; Centenas[1] := 'DOSCIENTOS'; Centenas[2] := 'TRESCIENTOS'; Centenas[3] := 'CUATROCIENTOS';
Centenas[4] := 'QUINIENTOS'; Centenas[5] := 'SEISCIENTOS'; Centenas[6] := 'SETECIENTOS'; Centenas[7] := 'OCHOCIENTOS'; Centenas[8] := 'NOVECIENTOS';

Cantidad := Trunc(curCantidad);
Centavos := (curCantidad - Cantidad) * 100;
NumeroBloques := 1;
Repeat
 PrimerDigito := 0;
 SegundoDigito := 0;
 TercerDigito := 0;
 Bloque := '';
 BloqueCero := 0;
 For i := 1 To 3 do begin
  Digito := Round(Cantidad) Mod 10;
  If Digito <> 0 Then begin
   Case i of
    1: begin
     Bloque := ' ' + Unidades[Digito - 1];
     PrimerDigito := Digito;
    end; //case 1
    2: begin
      If Digito <= 2 Then begin
       Bloque := ' ' + Unidades[(Digito * 10 + PrimerDigito - 1)];
      end Else begin
       If PrimerDigito <> 0 then
        Temp := ' Y' else Temp := '';
       Bloque := ' ' + Decenas[Digito - 1] + Temp + Bloque;
      End; //if
      SegundoDigito := Digito;
     end; //case 2
    3: begin
     If (Digito = 1) and (PrimerDigito = 0) and (SegundoDigito = 0) then
      Temp := 'CIEN' else Temp := Centenas[Digito-1];
     Bloque := ' ' + Temp + Bloque;
     TercerDigito := Digito;
     end; //case 3
    End; //case
  end Else begin
  BloqueCero := BloqueCero + 1;
  End; // If Digito <>0
  Cantidad := Int(Cantidad / 10);
  If Cantidad = 0 Then begin
   Break;
  End; // If Cantidad=0
 end; //for
 Case NumeroBloques of
  1:
   Resultado := Bloque;
  2: begin
   if BloqueCero = 3 then
    Temp := ' ' else Temp := ' MIL';
   Resultado := Bloque + Temp + Resultado;
   end; //case 2
  3: begin
   If (PrimerDigito = 1) and (SegundoDigito = 0) and (TercerDigito = 0) then
    Temp := ' MILLON' else Temp := ' MILLONES';
   Resultado := Bloque + Temp + Resultado;
   end; //case 3
 End; //case
 NumeroBloques := NumeroBloques + 1;
Until Cantidad = 0; //repeat
case MonNal of
 0: begin
 If curCantidad > 1 then
  Temp := ' CENTIMOS ###' else Temp := ' CENTIMO ###';
 CantidadEnLetra := Resultado + Temp;

 end;
 1: begin
   If curCantidad > 1 then
    Temp := ' EUROS ' else Temp := ' EURO ';
   if Centavos=0 then strCentavos := '###' else strCentavos := 'CON'+CantidadEnLetra(Centavos, 0);
   CantidadEnLetra := '###' + Resultado + Temp + strCentavos;
 end;
 2: begin
  If curCantidad > 1 then
   Temp := ' EUROS ' else Temp := ' EURO ';
   if Centavos=0 then strCentavos := '###' else strCentavos := 'CON'+CantidadEnLetra(Centavos, 0);
   CantidadEnLetra := '###' + Resultado + Temp + strCentavos;
 end;
end;

Espero podais ayudarme un poco con esto, es prácticamente lo único que me falta del programa.

Gracias de antemano por vuestra ayuda.

Un saludo.

TiammatMX 13-05-2014 14:07:01

Cita:

Empezado por Jovalca (Mensaje 476355)
...de estos mismos foros para pasar un numero a letras, tipo 1.220 a "Mil doscientos veinte".
Todo va bien con casi todos los números, he probado un montón y parece que todo va bien, pero cuando pones 1000, el texto muestra "UN MIL" en vez de "MIL"...

Que yo sepa y recuerde, "un mil" es CORRECTO en español..., tanto sintáctica como gramaticalmente...

Aún en inglés se construye con "one thousand", así que no, no veo dónde podría estar el problema, excepto en las convenciones sociales y comerciales sobre la expresión y lectura de una cantidad.

nlsgarcia 13-05-2014 16:50:36

Jovalca,

Cita:

...Problema con Numero a Letra - Muestra "Un Mil" en vez de "Mil"...
Revisa este código:
Código Delphi [-]
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    Edit1: TEdit;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

// Convierte numeros a letras de forma recursiva

function NumbersToLetters(Number: Double): string;

const
  Numbers: array[1..9] of String = ('Uno', 'Dos', 'Tres', 'Cuatro',
    'Cinco', 'Seis', 'Siete', 'Ocho', 'Nueve');

  Numbers2: array[11..19] of String = ('Once', 'Doce', 'Trece', 'Catorce',
    'Quince', 'Diez y Seis', 'Diez y Siete', 'Diez y Ocho', 'Diez y Nueve');

  Tenths: array[1..9] of String = ('Diez', 'Veinte', 'Trienta', 'Cuarenta',
    'Cincuenta', 'Sesenta', 'Setenta', 'Ochenta', 'Noventa');

  Hundreds : array[1..9] of String = ('Cien ', 'Docientos ', 'Trecientos ', 'Cuatrocientos ',
    'Quinientos ', 'Seicientos ', 'Setecientos ', 'Ochocientos ', 'Novecientos ');

  Min = 1.00;
  Max = 1000000000.00;
  
  function RecurseNumber(N: LongWord): string;
  begin
    case N of

      1..9:
        begin
           Result := Numbers[N];
        end;

      11..19:
        begin
           Result := Numbers2[N]
        end;

      10,20..99:
        begin
           if (N Mod 10) = 0 then
              Result := Tenths[N div 10] + RecurseNumber(N mod 10)
           else
              Result := Tenths[N div 10] + ' y '  + RecurseNumber(N mod 10);
        end;

      100..999:
      begin
        if (N = 100) or (N >=200) then Result := Hundreds[N div 100] + RecurseNumber(N mod 100);
        if (N >100) and (N<200) then Result := 'Ciento ' + RecurseNumber(N mod 100);
      end;

      1000..999999:
      begin
         if (Number >=1000) and (Number < 2000) then
            Result := 'Un Mil ' + RecurseNumber(N mod 1000)
         else
            Result := RecurseNumber(N div 1000) + ' Mil ' + RecurseNumber(N mod 1000);
      end;

      1000000..999999999:
      begin
         if (Number>=1000000) and (Number<2000000) then
            Result := 'Un Millon ' + RecurseNumber(N mod 1000000)
         else
            Result := RecurseNumber(N div 1000000) + ' Millones ' + RecurseNumber(N mod 1000000);
      end;

    end; {Case N of}

  end; {RecurseNumber}

begin
  if (Number >= Min) and (Number < Max) then
     begin
        Result := RecurseNumber(Round(Int(Number)));
        Result := Result +  ' con ' + Format('%.2d',[Round(Frac(Number) * 100)]) + '/100';
     end
  else
     Result := '-1';
end;

procedure TForm1.Button1Click(Sender: TObject);
var
   N1 : Double;
begin
   if TryStrToFloat(Edit1.Text,N1) then 
      ShowMessage(NumbersToLetters(N1)); 
end;

end.
El código anterior en Delphi 7 bajo Windows 7 Professional x32, convierte recursivamente números a letras en el rango de 1.00 a 999999999.99 teniendo la posibilidad de cambiar un mil por mil, sin embargo es más preciso y seguro al momento de hacer un cheque usar un mil en vez de mil. Un ejemplo de conversión es el que se muestra en la siguiente imagen:



Espero sea útil :)

Nelson.

Jovalca 13-05-2014 17:26:46

Gracias a los dos por responder.

Yo tampoco creo que sea incorrecta la expresión UN MIL, sólo que la gente por lo general esta acostumbra a leer o escribir MIL EUROS en vez de UN MIL EUROS, más que nada era por eso.

En cuanto al código, creo que lo dejaré así ya que el que tengo contempla traducir también los decimales. Solo quería saber si se podia quitar fácilmente el UN.

Muchas gracias de nuevo a los dos.

Un Saludo.

aposi 14-05-2014 16:47:44

Código Delphi [-]

 
    2: begin    
       if BloqueCero = 3 then
          Temp := ' ' 
      else Temp := ' MIL';
      if Bloque = 'UN' then Resultado := Temp + Resultado;
      else Resultado := Bloque + Temp + Resultado;   
     end;

Prueba con esta modificación:
se trata de a la hora de moner el mil, si el numero es 'UN' que no lo ponga
creo que no fallara en ningun numero.

Jovalca 19-06-2014 15:42:01

Gracias !! Un saludo.


La franja horaria es GMT +2. Ahora son las 09:52:57.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi