PDA

Ver la Versión Completa : Concatenar un numero determinado de palabras con el contenido de un array


webmasterplc
10-05-2014, 14:20:04
Buenas Tengo una función la cual me hace el envio de sms a travez de un gateway, esta funcion lo hace correctamente, para enviar masivos hago la consulta sql y la cargo en un array y luego hay un ciclo recorriendo el array pro a veces son 1000 registros y tarda mucho y a veces me da un error,el gateway me permite concatenar numeros con ; hasta 500 y alli hace una sola petición pos miestras que como lo hago hace 1000 peticiones, como podre hacer para concatenar y eliminar el ultimo numero el punto y coma que le queda al final este es el codigo.
function enviarSMS (phone,mensaje : string) : string;
var
http: TIdHttp;
params: TStrings;
respuesta: string;
begin
http := TIdHTTP.Create(nil);
params := TStringList.Create;
begin
params.Add('usuario=miusuario');
params.Add('clave=AprilApril1979');
params.Add('telefonos='+phone);
params.Add('texto='+mensaje);
respuesta := http.Post('http://www.enlinea-ve.com/webservices/' + 'SendSms', params);
end;
params.Free;
http.Free;
end;

el array esta creado en la unidad

contactos: array of string;

y llamo la funcion asi
with datos.sqcontactos do
begin
Close;
SQL.Text:= 'SELECT * FROM vcontactos WHERE vcontactos.miem_clasificacion =: miem_clasificacion';
ParamByName('miem_clasificacion').AsString:=cbbclasificacion.Text;
Open;
while not Eof do
begin
SetLength(contactos, Length(contactos)+1);
contactos[High(contactos)] := FieldByName('celular').AsString;
Next;
end;
end;
try
for i:= Low(contactos) to High(contactos) do
begin
enviarSMS((Format('%s', [contactos[i]])),mmomensaje.Text);
end;
finally
contactos:=nil;
lst1.Clear;
mmomensaje.Clear;
MessageDlg('Proceso de Envío de SMS Concluido Exitosmente', mtCustom, [mbOK], 0);
end;
Lo Otro es que como ven solo paso el numero al array quisiera ver si es posible pasarle numero y nombre a un array para personalizar el mensaje de texto cuando sea necesario.

Gracias de Antemano

ecfisa
10-05-2014, 19:31:35
Hola webmasterpcl.

Voy a empezar por el final.
Lo Otro es que como ven solo paso el numero al array quisiera ver si es posible pasarle numero y nombre a un array para personalizar el mensaje de texto cuando sea necesario.

De este modo podes enviarle los datos que desees mediante un arreglo dinámico:

...
type
TRecip = record
Nombre: string;
Numero: string;
//...
end;

var
contactos: array of TRecip;

function enviarSMS (Recip: TRecip; Mensaje: string): string;
var
http: TIdHttp;
params: TStrings;
respuesta: string;
begin
http := TIdHTTP.Create(nil);
params := TStringList.Create;
try
params.Add('usuario=miusuario');
params.Add('clave=AprilApril1979');
params.Add('Nombre=' + Recip.Nombre);
params.Add('telefonos=' + Recip.Numero);
params.Add('texto=' + Mensaje);
Result := http.Post('http://www.enlinea-ve.com/webservices/' + 'SendSms', params);
finally
params.Free;
http.Free;
end;
end;


En el uso tendras que modificar:

with datos.sqcontactos do
begin
Close;
SQL.Text:= 'SELECT * FROM vcontactos WHERE vcontactos.miem_clasificacion =: miem_clasificacion';
ParamByName('miem_clasificacion').AsString:=cbbclasificacion.Text;
Open;
while not Eof do
begin
SetLength(contactos, Length(contactos)+1);
// * Aquí *
contactos[High(contactos)].Nombre:= FieldByName('Nombre').AsString;
contactos[High(contactos)].Numero:= FieldByName('celular').AsString;
Next;
end;
end;
try
for i:= Low(contactos) to High(contactos) do
enviarSMS(contactos[i], Memo1.Text); // * Y aquí *
finally
contactos:=nil;
lst1.Clear;
mmomensaje.Clear;
MessageDlg('Proceso de Envío de SMS Concluido Exitosmente', mtCustom, [mbOK], 0);
end;


...hasta 500 y alli hace una sola petición pos miestras que como lo hago hace 1000 peticiones, como podre hacer para concatenar y eliminar el ultimo numero el punto y coma que le queda al final este es el codigo.
No termino de comprender esta parte, pero para eliminar el último el último caracter de una cadena:

SetLength(un_string, Length(un_string) - 1);


Saludos :)

webmasterplc
10-05-2014, 22:00:55
Osea me gustaria contatenar de 500 en 500 separados por (;) pero si le agredo un punto y coma despues de cada numero me va a quedar un (;) al final y me dara error en vez de pasarle un numero a la vez le pasaria 584240000000;584260000000; y los enviaria e en una sola peticion 500 sms , lo que me respondiste esta genial para personalizar el mensaje pero cuando no quiero personalizarlo solo hago una sola peticion de numeros concatenados por ;

ecfisa
10-05-2014, 22:19:36
Hola webmasterplc.
Osea me gustaria contatenar de 500 en 500 separados por (;) pero si le agredo un punto y coma despues de cada numero me va a quedar un (;) al final y me dara error en vez de pasarle un numero a la vez le pasaria 584240000000;584260000000; y los enviaria e en una sola peticion 500 sms , lo que me respondiste esta genial para personalizar el mensaje pero cuando no quiero personalizarlo solo hago una sola peticion de numeros concatenados por ;
Entonces es como te sugerí en la última parte del mensaje anterior.

Hace esta simple prueba:

procedure TForm1.Button1Click(Sender: TObject);
var
s: string;
begin
s:= '584240000000;584260000000;584280000000;584300000000;';
SetLength(s,Length(s)-1);
ShowMessage(s);
end;

La variable s termina con el valor: '584240000000;584260000000;584280000000;584300000000' (sin finalizar en ";") que es precisamente lo que estas buscando.

Saludos :)

webmasterplc
11-05-2014, 14:24:45
lo que busco en realidad es enviarlo de dos formas a la funcion, una ir recorriendo el array numero por numero y haciendo la petición uno a la vez que me permitiria personalizar cada mensaje y de la otra recorrer el array y concatenar los numeros de 500 numeros en 500 y si hay mil solo hago dos peticiones de envio de sms

ecfisa
11-05-2014, 22:13:28
Hola webmasterplc.

Por lo que comentas en el mensaje #3 la parte de personalizar ya la tenes encaminada, pero creo que no me has entendido sobre como procesar el punto y coma cuando envias el lote de 1000 mensajes.

A ver si con este ejemplo me explico mas claramente:

var
h, l, m: Integer;
begin
// Asumo que contactos ya tiene asignado los 1000 números
l:= Low(contactos);
m:= High(contactos) div 2;
h:= High(contactos);

// quitar ";" al contacto 500
SetLength(contactos[m], Length(contactos[m])-1);
// quitar ";" al contacto 1000
SetLength(contactos[h], Length(contactos[h])-1);

// Visualizar el resultado
ShowMessage(Format('000-499: %s %s%s500-999: %s %s',
[contactos[l],contactos[m],#10,contactos[m+1],contactos[h]]));
...

Cuando envíes "contáctos" como argumento los datos 500 y 1000 ya no terminarán en ";".

Saludos :)

webmasterplc
12-05-2014, 15:28:45
Gracias hermano ahorita voy a trabajar con esta, lo de concatenar lo tengo listo me faltaba esto, la cantidad de numeros no son siempre 1000 pueden ser mal loque tengo es que dividirlos de 500 en 500 saludos

ecfisa
12-05-2014, 19:24:20
Hola webmasterplc.
... lo que tengo es que dividirlos de 500 en 500 saludos
Correcto y es claro que el último lote generalmente será menor, por ejemplo:

var
lotes: Integer;
Resto: Integer;
begin
Lotes := High(contactos) div 500;
Resto := High(Contactos)-Lotes*500;
ShowMessage(Format('Enviando %d lotes de 500 mensajes%sy uno de %d',
[Lotes,#10,Resto]));
end;


Saludos :)

webmasterplc
02-07-2014, 05:56:22
Retomando este hilo brother ya hice la funcion concatenar
le paso los parametros del array y me concatena bien quitando la (,) como queria
ahora solo me falta controlar que cuando recorra los primeros 500 registros haga una accion y luego retome donde quedo y continue y al llegar a 500 haga la accion y si aun hay elentos continue

algo asi como esto

if tope < 500 then
begin
for i:= Low(contactos) to High(contactos) do
begin
Concatenar((Format('%s', [contactos[i]])));
tope:=tope+1;
end;
end