Secciones de la página

txt. tol


Declaraciones


Funciones de nombre corto


Funciones


Time oriented language


Árbol de ficheros

Funciones

Text Q()

Text F()

Real TxtBeginStrict()

Text TxtBetween2Tag()

Text TxtCat()

Real TxtEndStrict()

Set TxtForChr()

Set TxtLineWrap()

Set TxtSplitBy1Tag()

Set TxtSplitBy2Fast()

Set TxtSplitBy2Tag()

Set TxtTokenizer()

Tol

Artículos del sitio

Presentación de Tol

Todos los programas

Simuladores visuales

Sitios que me gustan

Por categorías

Algoritmia

Búsqueda y ordenación

Computación fisiológica

Editorial y edición

Gráficos de datos

Herramientas y utilidades

Hipertexto

Informática forense

Lectura óptica de datos

Metaprogramación

No determinista

Ofimática

Recursión e iteración

Reglas y restricciones

Series y estadística









txt.tol de Dct.Writer

Funciones de textos.

Declaraciones

Funciones de nombre corto

  • Text Q(Text txtVal)
    Retorna un texto entre dobles comillas. Equivalente a la funcion Tol Qt().
  • Text F(Anything anyVal)
    Retorna numeros, fechas, textos, conjuntos como un texto de formato simple.

Funciones

  • Real TxtBeginStrict(Text txtInp, Text txtIni)
    Version estricta de TextBeginWith(), da falso siempre que txtIni sea nulo.
  • Text TxtBetween2Tag(Text inpTxt, Text tagIni, Text tagEnd, Real cmpFlg)
    Retorna un subtexto entre la primera ocurrencia de tagIni y tagEnd. Si tagIni o tagEnd no aparecen retorna la tira vacia. Si cmpFlg es cierto entonces aplica la funcion Compact() al texto que retorna. Por ejemplo: TxtBetween2Tag('a b [[ c ]] d [[ e ]] f', '[[', ']]', TRUE) retorna 'c'.
  • Text TxtCat(Text iniTxt, Text sepTxt, Text endTxt)
    Retorna un texto resultado de concatenar 2 textos con un separador en medio, si alguno de los 2 textos son la tira vacia retorna el otro texto.
  • Real TxtEndStrict(Text txtInp, Text txtEnd)
    Version estricta de TextEndAt(), da falso siempre que txtEnd sea nulo.
  • Set TxtForChr(Text inpTxt, Code funChr)
    Retorna el conjunto resultado de aplicar la funcion funChr(Text oneChr) a todos los caracteres del texto de entrada txtInp. Retorna un Set a imagen de las funciones basicas For() y EvalSet().
  • Set TxtLineWrap(Text txtInp, Real linMax, Real cmpCtr)
    Retorna un conjunto de 2 texto el primero con un máximo de linMax caracteres y el segundo con el resto. Es el resultado de cortar txtInp por el primer blanco que permita que el corte cumpla la condición inicial. Si el texto de entrada es mas corte que linMax retorna un conjunto formado por el texto inicial y la tira vacia. Si el corte es imposible busca el mejor corte posible y si no lo encuentra retorna un conjunto formado por el texto inicial y la tira vacia. Si cmpCtr es true los resultados son compactados. Tambien existe en Tol la funcion Wrap() con ciertas semejanzas, aunque mas a TxtParagraphWrap().
  • Set TxtSplitBy1Tag(Text txtInp, Text tagBrk)
    Retorna un conjunto de textos resultado de cortar el texto de entrada por un unico tag tagBrk incluyendo dicho tagBrk al inicio y al final de cada texto que enmarca, las ocurrencias impares de tagBrk al inicio del texto y las impares al final. Tiene mas sentido cuando el numero de ocurrencias de tagBrk es par. Si el numero de ocurrencias de tagbrk es impar funciona como si al final del texto txtInp hubiera una ultima ocurrencia. Fue una funcion recursiva, pero la versión 2.0.1 de Tol se caia con textos grandes, ahora es una funcion iterativa. TxtSplitBy1Tag(aaa|::|bbb|---|ccc, |) -> [aaav, |::|, bbb, |---|, ccc].
  • Set TxtSplitBy2Fast(Text txtInp, Text tagIni, Text tagEnd)
    Retorna un conjunto de textos resultado de cortar el texto de entrada por dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de cada texto que enmarcan. Los tags tagIni y tabEnd no han de ser nulos ni iguales, si son iguales lo correcto seria utilizar la funcion TxtSplitBy1Tag(). No es una funcion recursiva, es mas rapida que TxtSplitBy2Tag() pero menos resistente a la reiteracion de tags de inicio con un unico final. No funciona correctamente si los tags inicial y final son iguales. Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final. TxtSplitBy2Fast(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].
  • Set TxtSplitBy2Tag(Text txtInp, Text tagIni, Text tagEnd)
    Retorna un conjunto de textos resultado de cortar el texto de entrada por un dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de cada texto que enmarcan. Los tags tagIni y tabEnd no han de ser nulos. Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final. Es una funcion recursiva. Si funciona correctamente si los tags inicial y final son iguales. TxtSplitBy2Tag(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].
  • Set TxtTokenizer(Text txtInp, Text tagBrk)
    Retorna un conjunto de textos resultado de cortar el texto de entrada por un unico tag tagBrk no incluyendo el tag tagBrk dentro de los textos. Se soporta en la funcion Tol Tokenizer() que rompe por un unico caracter. Usa como caracter interno de corte el 7 (bell), esperando que no aparezca.

Funciones de nombre corto

Text Q()

//////////////////////////////////////////////////////////////////////////////
Text Q(Text txtVal) // Text
//////////////////////////////////////////////////////////////////////////////
{ Char(34) + txtVal + Char(34) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un texto entre dobles comillas. Equivalente a la funcion Tol Qt().",
Q);
//////////////////////////////////////////////////////////////////////////////

Text F()

//////////////////////////////////////////////////////////////////////////////
Text F(Anything anyVal)
//////////////////////////////////////////////////////////////////////////////
{
  Text graVal = Grammar(anyVal);
  Case
  (
    graVal=="Text", anyVal, // Ya es texto

    graVal=="Real", If(EQ(anyVal, Round(anyVal)),
                       FormatReal(anyVal, "%.0lf"),  // Entero sin decimales
                       FormatReal(anyVal, "%.2lf")), // 2 decimales

    graVal=="Date", If(Hour(anyVal),
                       FormatDate(anyVal, "%c%Y/%m/%d %h:%i:%s"), // Tiempo
                       FormatDate(anyVal, "%c%Y/%m/%d")),         // Fecha

    graVal=="Set",
    {
      Real crdSet = Card(anyVal);
      Case(
      EQ(crdSet,0), "[]",
      EQ(crdSet,1), "["+F(anyVal[1])+"]",
      TRUE,         "["+F(anyVal[1])+SetSum(For(2,crdSet,Text(Real setPos)
                  { "|"+F(anyVal[setPos]) }))+"]")
    },
    
    TRUE,           "Not basic type"
  )
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna numeros, fechas, textos, conjuntos como un texto de formato simple.",
F);
//////////////////////////////////////////////////////////////////////////////

Funciones

Real TxtBeginStrict()

//////////////////////////////////////////////////////////////////////////////
Real TxtBeginStrict(Text txtInp, // Texto de entrada
                    Text txtIni) // Texto inicial
//////////////////////////////////////////////////////////////////////////////
{ If(txtIni=="", FALSE, TextBeginWith(txtInp, txtIni)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Version estricta de TextBeginWith(), da falso siempre que txtIni sea nulo.",
TxtBeginStrict);
//////////////////////////////////////////////////////////////////////////////

Text TxtBetween2Tag()

//////////////////////////////////////////////////////////////////////////////
Text TxtBetween2Tag(Text inpTxt, // Texto de entrada
                    Text tagIni, // Tag inicial
                    Text tagEnd, // Tag final
                    Real cmpFlg) // Si true aplica Compact()
//////////////////////////////////////////////////////////////////////////////
{
  Real posIni = TextFind(inpTxt, tagIni);
  Text result = If(LE(posIni,0), "",
  {
    Real lenIni = TextLength(tagIni);
    Real posSub = posIni + lenIni;
    Real posEnd = TextFind(inpTxt, tagEnd, posSub);
    If(LE(posEnd, 0), "", Sub(inpTxt, posSub, posEnd-1))
  });
  If(cmpFlg, Compact(result), result)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un subtexto entre la primera ocurrencia de tagIni y tagEnd.
Si tagIni o tagEnd no aparecen retorna la tira vacia.
Si cmpFlg es cierto entonces aplica la funcion Compact() al texto que retorna.
Por ejemplo:
  TxtBetween2Tag('a b [[ c ]] d [[ e ]] f', '[[', ']]', TRUE)
  retorna 'c'.",
TxtBetween2Tag);
//////////////////////////////////////////////////////////////////////////////

Text TxtCat()

//////////////////////////////////////////////////////////////////////////////
Text TxtCat(Text iniTxt, // Texto inicial
            Text sepTxt, // Texto de separacion
            Text endTxt) // Texto final
//////////////////////////////////////////////////////////////////////////////
{
  Case(
    iniTxt=="", endTxt,
    endTxt=="", iniTxt,
    TRUE,       iniTxt + sepTxt + endTxt)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un texto resultado de concatenar 2 textos con un separador en medio,
si alguno de los 2 textos son la tira vacia retorna el otro texto.",
TxtCat);
//////////////////////////////////////////////////////////////////////////////

Real TxtEndStrict()

//////////////////////////////////////////////////////////////////////////////
Real TxtEndStrict(Text txtInp, // Texto de entrada
                  Text txtEnd) // Texto final
//////////////////////////////////////////////////////////////////////////////
{ If(txtEnd=="", FALSE, TextEndAt(txtInp, txtEnd)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Version estricta de TextEndAt(), da falso siempre que txtEnd sea nulo.",
TxtEndStrict);
//////////////////////////////////////////////////////////////////////////////

Set TxtForChr()

//////////////////////////////////////////////////////////////////////////////
Set TxtForChr(Text inpTxt, // Texto de entrada
              Code funChr) // Funcion tipo Anything(Text oneChr)
//////////////////////////////////////////////////////////////////////////////
{
  Real lenTxt = TextLength(inpTxt);
  For(1, lenTxt, Anything(Real posTxt) { funChr(Sub(inpTxt,posTxt,posTxt)) })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna el conjunto resultado de aplicar la funcion funChr(Text oneChr)
a todos los caracteres del texto de entrada txtInp.
Retorna un Set a imagen de las funciones basicas For() y EvalSet().",
TxtForChr);
//////////////////////////////////////////////////////////////////////////////

Set TxtLineWrap()

//////////////////////////////////////////////////////////////////////////////
Set  TxtLineWrap(Text txtInp, // Texto de entrada
                 Real linMax, // Maximo numero de caracteres por linea
                 Real cmpCtr) // Si true entonces compacta
//////////////////////////////////////////////////////////////////////////////
{
  Text txtCmp = If(cmpCtr, Compact(txtInp), txtInp);
  Text txtRev = Reverse(txtCmp);
  Real txtLen = TextLength(txtCmp);
  Set  cutSet = If(LE(txtLen, linMax), [[txtCmp, ""]], // Ya esta hecho
  {
    Real blkPos = TextFind(txtRev, " ", txtLen-linMax); // Busca para atras

    If(GE(blkPos, 1),
    {
      SetOfText(Sub(txtCmp, 0,               txtLen-blkPos),
                Sub(txtCmp, txtLen-blkPos+1, txtLen))
    },
    {
      // No se puede cortar
      Real blkBad = TextFind(txtCmp, " ", linMax+1); // Busca hacia adelante

      If(LT(blkBad, 0), [[txtCmp, ""]], // No hay corte posible
      {
        SetOfText(Sub(txtCmp, 0,        blkBad-1), // Hay un mal corte
                  Sub(txtCmp, blkBad+1, txtLen))
      })
    })
  });
  If(cmpCtr, SetOfText(Compact(cutSet[1]),Compact(cutSet[2])), cutSet)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de 2 texto el primero con un máximo de linMax caracteres
y el segundo con el resto.
Es el resultado de cortar txtInp por el primer blanco que permita que el corte
cumpla la condición inicial.
Si el texto de entrada es mas corte que linMax retorna un conjunto formado
por el texto inicial y la tira vacia.
Si el corte es imposible busca el mejor corte posible y si no lo encuentra
retorna un conjunto formado por el texto inicial y la tira vacia.
Si cmpCtr es true los resultados son compactados.
Tambien existe en Tol la funcion Wrap() con ciertas semejanzas,
aunque mas a TxtParagraphWrap().",
TxtLineWrap);
//////////////////////////////////////////////////////////////////////////////

Set TxtSplitBy1Tag()

//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy1Tag(Text txtInp, // Texto de entrada
                   Text tagBrk) // Tag por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Set txtTok = TxtTokenizer(txtInp, tagBrk);
  For(1, Card(txtTok), Text(Real posTok) // Ciclo para impares y pares
  { If(posTok%2, txtTok[posTok], tagBrk+txtTok[posTok]+tagBrk) })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
unico tag tagBrk incluyendo dicho tagBrk al inicio y al final de cada texto
que enmarca, las ocurrencias impares de tagBrk al inicio del texto y
las impares al final.
Tiene mas sentido cuando el numero de ocurrencias de tagBrk es par.
Si el numero de ocurrencias de tagbrk es impar funciona como si al final del
texto txtInp hubiera una ultima ocurrencia.
Fue una funcion recursiva, pero la versión 2.0.1 de Tol se caia con textos
grandes, ahora es una funcion iterativa.
TxtSplitBy1Tag(aaa|::|bbb|---|ccc, |) -> [aaav, |::|, bbb, |---|, ccc].",
TxtSplitBy1Tag);
//////////////////////////////////////////////////////////////////////////////

Set TxtSplitBy2Fast()

//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy2Fast(Text txtInp, // Texto de entrada
                    Text tagIni, // Tag inicial por el que se corta
                    Text tagEnd) // Tag final por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Text chrBrk = Char(7); // Caracter auxiliar de corte que se espera unico
  Text repEnd = Replace(txtInp, tagEnd, tagEnd+chrBrk);
  Set  txtSet = Tokenizer(repEnd, chrBrk);

  Set  cicSet = EvalSet(txtSet, Set(Text txtTok)
  {

    Text repIni = Replace(txtTok, tagIni, chrBrk+tagIni);
    Set  tokSet = Tokenizer(repIni, chrBrk);
    Select(tokSet, Real(Text tokTxt) { tokTxt != "" }) // Elimina los vacios
  });
  BinGroup("<<", cicSet) // De conjunto de pares a conjunto lineal
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por
dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de
cada texto que enmarcan.
Los tags tagIni y tabEnd no han de ser nulos ni iguales, si son iguales lo
correcto seria utilizar la funcion TxtSplitBy1Tag().
No es una funcion recursiva, es mas rapida que TxtSplitBy2Tag() pero menos
resistente a la reiteracion de tags de inicio con un unico final.
No funciona correctamente si los tags inicial y final son iguales.
Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final.
TxtSplitBy2Fast(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].",
TxtSplitBy2Fast);
//////////////////////////////////////////////////////////////////////////////

Set TxtSplitBy2Tag()

//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy2Tag(Text txtInp, // Texto de entrada
                   Text tagIni, // Tag inicial por el que se corta
                   Text tagEnd) // Tag final por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Real posIni = TextFind(txtInp, tagIni);
  If(LE(posIni,0), SetOfText(txtInp), // Nada que cortar
  {
    Real lenTxt = TextLength(txtInp); // Longitud del texto de entrada
    Real lenIni = TextLength(tagIni); // Longitud del tag inicial
    Real lenEnd = TextLength(tagEnd); // Longitud del tag final
    Real posSub = posIni + lenIni;
    Real posEnd = TextFind(txtInp, tagEnd, posSub);
    Case(
      Or(And(EQ(posIni,1),LE(posEnd,0)), // Ini en posicion 1 pero no termina
         And(EQ(posIni,1),EQ(posEnd+lenEnd-1,lenTxt))), // Justo ini y final
         SetOfText(txtInp),
      Or(And(GT(posIni,1),LE(posEnd,0)), // Ini en posicion >1 pero no termina
         And(GT(posIni,1),EQ(posEnd+lenEnd-1,lenTxt))), // Justo al final
         SetOfText(
           Sub(txtInp, 1,      posIni-1),
           Sub(txtInp, posIni, lenTxt)),
      And(EQ(posIni,1),GT(posEnd,1)), // Inicia en posicion 1, termina y sigue
        SetOfText(
          Sub(txtInp, 1,       posEnd+lenEnd-1)) <<
          TxtSplitBy2Tag(Sub(txtInp, posEnd+lenEnd, lenTxt), tagIni, tagEnd),
      TRUE,                           // Inicia posicion >1, termina y sigue
        SetOfText(
          Sub(txtInp, 1,       posIni-1),
          Sub(txtInp, posIni,  posEnd+lenEnd-1)) <<
          TxtSplitBy2Tag(Sub(txtInp, posEnd+lenEnd, lenTxt), tagIni, tagEnd))
  })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de
cada texto que enmarcan.
Los tags tagIni y tabEnd no han de ser nulos.
Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final.
Es una funcion recursiva.
Si funciona correctamente si los tags inicial y final son iguales.
TxtSplitBy2Tag(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].",
TxtSplitBy2Tag);
//////////////////////////////////////////////////////////////////////////////

Set TxtTokenizer()

//////////////////////////////////////////////////////////////////////////////
Set TxtTokenizer(Text txtInp, // Texto de entrada
                 Text tagBrk) // Tag por el que se corta
//////////////////////////////////////////////////////////////////////////////
{ Tokenizer(Replace(txtInp, tagBrk, Char(7)), Char(7)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
unico tag tagBrk no incluyendo el tag tagBrk dentro de los textos.
Se soporta en la funcion Tol Tokenizer() que rompe por un unico caracter.
Usa como caracter interno de corte el 7 (bell), esperando que no aparezca.",
TxtTokenizer);
//////////////////////////////////////////////////////////////////////////////

Time oriented language

//////////////////////////////////////////////////////////////////////////////
// FILE    : txt.tol
// AUTHOR  : http://www.asolver.com
// PURPOSE : Funciones de textos.
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
// SHORTNAMES
//////////////////////////////////////////////////////////////////////////////

//////////////////////////////////////////////////////////////////////////////
Text Q(Text txtVal) // Text
//////////////////////////////////////////////////////////////////////////////
{ Char(34) + txtVal + Char(34) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un texto entre dobles comillas. Equivalente a la funcion Tol Qt().",
Q);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Text F(Anything anyVal)
//////////////////////////////////////////////////////////////////////////////
{
  Text graVal = Grammar(anyVal);
  Case
  (
    graVal=="Text", anyVal, // Ya es texto

    graVal=="Real", If(EQ(anyVal, Round(anyVal)),
                       FormatReal(anyVal, "%.0lf"),  // Entero sin decimales
                       FormatReal(anyVal, "%.2lf")), // 2 decimales

    graVal=="Date", If(Hour(anyVal),
                       FormatDate(anyVal, "%c%Y/%m/%d %h:%i:%s"), // Tiempo
                       FormatDate(anyVal, "%c%Y/%m/%d")),         // Fecha

    graVal=="Set",
    {
      Real crdSet = Card(anyVal);
      Case(
      EQ(crdSet,0), "[]",
      EQ(crdSet,1), "["+F(anyVal[1])+"]",
      TRUE,         "["+F(anyVal[1])+SetSum(For(2,crdSet,Text(Real setPos)
                  { "|"+F(anyVal[setPos]) }))+"]")
    },
    
    TRUE,           "Not basic type"
  )
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna numeros, fechas, textos, conjuntos como un texto de formato simple.",
F);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
// FUNCTIONS
//////////////////////////////////////////////////////////////////////////////

//////////////////////////////////////////////////////////////////////////////
Real TxtBeginStrict(Text txtInp, // Texto de entrada
                    Text txtIni) // Texto inicial
//////////////////////////////////////////////////////////////////////////////
{ If(txtIni=="", FALSE, TextBeginWith(txtInp, txtIni)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Version estricta de TextBeginWith(), da falso siempre que txtIni sea nulo.",
TxtBeginStrict);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Text TxtBetween2Tag(Text inpTxt, // Texto de entrada
                    Text tagIni, // Tag inicial
                    Text tagEnd, // Tag final
                    Real cmpFlg) // Si true aplica Compact()
//////////////////////////////////////////////////////////////////////////////
{
  Real posIni = TextFind(inpTxt, tagIni);
  Text result = If(LE(posIni,0), "",
  {
    Real lenIni = TextLength(tagIni);
    Real posSub = posIni + lenIni;
    Real posEnd = TextFind(inpTxt, tagEnd, posSub);
    If(LE(posEnd, 0), "", Sub(inpTxt, posSub, posEnd-1))
  });
  If(cmpFlg, Compact(result), result)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un subtexto entre la primera ocurrencia de tagIni y tagEnd.
Si tagIni o tagEnd no aparecen retorna la tira vacia.
Si cmpFlg es cierto entonces aplica la funcion Compact() al texto que retorna.
Por ejemplo:
  TxtBetween2Tag('a b [[ c ]] d [[ e ]] f', '[[', ']]', TRUE)
  retorna 'c'.",
TxtBetween2Tag);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Text TxtCat(Text iniTxt, // Texto inicial
            Text sepTxt, // Texto de separacion
            Text endTxt) // Texto final
//////////////////////////////////////////////////////////////////////////////
{
  Case(
    iniTxt=="", endTxt,
    endTxt=="", iniTxt,
    TRUE,       iniTxt + sepTxt + endTxt)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un texto resultado de concatenar 2 textos con un separador en medio,
si alguno de los 2 textos son la tira vacia retorna el otro texto.",
TxtCat);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Real TxtEndStrict(Text txtInp, // Texto de entrada
                  Text txtEnd) // Texto final
//////////////////////////////////////////////////////////////////////////////
{ If(txtEnd=="", FALSE, TextEndAt(txtInp, txtEnd)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Version estricta de TextEndAt(), da falso siempre que txtEnd sea nulo.",
TxtEndStrict);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set TxtForChr(Text inpTxt, // Texto de entrada
              Code funChr) // Funcion tipo Anything(Text oneChr)
//////////////////////////////////////////////////////////////////////////////
{
  Real lenTxt = TextLength(inpTxt);
  For(1, lenTxt, Anything(Real posTxt) { funChr(Sub(inpTxt,posTxt,posTxt)) })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna el conjunto resultado de aplicar la funcion funChr(Text oneChr)
a todos los caracteres del texto de entrada txtInp.
Retorna un Set a imagen de las funciones basicas For() y EvalSet().",
TxtForChr);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set  TxtLineWrap(Text txtInp, // Texto de entrada
                 Real linMax, // Maximo numero de caracteres por linea
                 Real cmpCtr) // Si true entonces compacta
//////////////////////////////////////////////////////////////////////////////
{
  Text txtCmp = If(cmpCtr, Compact(txtInp), txtInp);
  Text txtRev = Reverse(txtCmp);
  Real txtLen = TextLength(txtCmp);
  Set  cutSet = If(LE(txtLen, linMax), [[txtCmp, ""]], // Ya esta hecho
  {
    Real blkPos = TextFind(txtRev, " ", txtLen-linMax); // Busca para atras

    If(GE(blkPos, 1),
    {
      SetOfText(Sub(txtCmp, 0,               txtLen-blkPos),
                Sub(txtCmp, txtLen-blkPos+1, txtLen))
    },
    {
      // No se puede cortar
      Real blkBad = TextFind(txtCmp, " ", linMax+1); // Busca hacia adelante

      If(LT(blkBad, 0), [[txtCmp, ""]], // No hay corte posible
      {
        SetOfText(Sub(txtCmp, 0,        blkBad-1), // Hay un mal corte
                  Sub(txtCmp, blkBad+1, txtLen))
      })
    })
  });
  If(cmpCtr, SetOfText(Compact(cutSet[1]),Compact(cutSet[2])), cutSet)
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de 2 texto el primero con un máximo de linMax caracteres
y el segundo con el resto.
Es el resultado de cortar txtInp por el primer blanco que permita que el corte
cumpla la condición inicial.
Si el texto de entrada es mas corte que linMax retorna un conjunto formado
por el texto inicial y la tira vacia.
Si el corte es imposible busca el mejor corte posible y si no lo encuentra
retorna un conjunto formado por el texto inicial y la tira vacia.
Si cmpCtr es true los resultados son compactados.
Tambien existe en Tol la funcion Wrap() con ciertas semejanzas,
aunque mas a TxtParagraphWrap().",
TxtLineWrap);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy1Tag(Text txtInp, // Texto de entrada
                   Text tagBrk) // Tag por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Set txtTok = TxtTokenizer(txtInp, tagBrk);
  For(1, Card(txtTok), Text(Real posTok) // Ciclo para impares y pares
  { If(posTok%2, txtTok[posTok], tagBrk+txtTok[posTok]+tagBrk) })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
unico tag tagBrk incluyendo dicho tagBrk al inicio y al final de cada texto
que enmarca, las ocurrencias impares de tagBrk al inicio del texto y
las impares al final.
Tiene mas sentido cuando el numero de ocurrencias de tagBrk es par.
Si el numero de ocurrencias de tagbrk es impar funciona como si al final del
texto txtInp hubiera una ultima ocurrencia.
Fue una funcion recursiva, pero la versión 2.0.1 de Tol se caia con textos
grandes, ahora es una funcion iterativa.
TxtSplitBy1Tag(aaa|::|bbb|---|ccc, |) -> [aaav, |::|, bbb, |---|, ccc].",
TxtSplitBy1Tag);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy2Fast(Text txtInp, // Texto de entrada
                    Text tagIni, // Tag inicial por el que se corta
                    Text tagEnd) // Tag final por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Text chrBrk = Char(7); // Caracter auxiliar de corte que se espera unico
  Text repEnd = Replace(txtInp, tagEnd, tagEnd+chrBrk);
  Set  txtSet = Tokenizer(repEnd, chrBrk);

  Set  cicSet = EvalSet(txtSet, Set(Text txtTok)
  {

    Text repIni = Replace(txtTok, tagIni, chrBrk+tagIni);
    Set  tokSet = Tokenizer(repIni, chrBrk);
    Select(tokSet, Real(Text tokTxt) { tokTxt != "" }) // Elimina los vacios
  });
  BinGroup("<<", cicSet) // De conjunto de pares a conjunto lineal
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por
dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de
cada texto que enmarcan.
Los tags tagIni y tabEnd no han de ser nulos ni iguales, si son iguales lo
correcto seria utilizar la funcion TxtSplitBy1Tag().
No es una funcion recursiva, es mas rapida que TxtSplitBy2Tag() pero menos
resistente a la reiteracion de tags de inicio con un unico final.
No funciona correctamente si los tags inicial y final son iguales.
Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final.
TxtSplitBy2Fast(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].",
TxtSplitBy2Fast);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set TxtSplitBy2Tag(Text txtInp, // Texto de entrada
                   Text tagIni, // Tag inicial por el que se corta
                   Text tagEnd) // Tag final por el que se corta
//////////////////////////////////////////////////////////////////////////////
{
  Real posIni = TextFind(txtInp, tagIni);
  If(LE(posIni,0), SetOfText(txtInp), // Nada que cortar
  {
    Real lenTxt = TextLength(txtInp); // Longitud del texto de entrada
    Real lenIni = TextLength(tagIni); // Longitud del tag inicial
    Real lenEnd = TextLength(tagEnd); // Longitud del tag final
    Real posSub = posIni + lenIni;
    Real posEnd = TextFind(txtInp, tagEnd, posSub);
    Case(
      Or(And(EQ(posIni,1),LE(posEnd,0)), // Ini en posicion 1 pero no termina
         And(EQ(posIni,1),EQ(posEnd+lenEnd-1,lenTxt))), // Justo ini y final
         SetOfText(txtInp),
      Or(And(GT(posIni,1),LE(posEnd,0)), // Ini en posicion >1 pero no termina
         And(GT(posIni,1),EQ(posEnd+lenEnd-1,lenTxt))), // Justo al final
         SetOfText(
           Sub(txtInp, 1,      posIni-1),
           Sub(txtInp, posIni, lenTxt)),
      And(EQ(posIni,1),GT(posEnd,1)), // Inicia en posicion 1, termina y sigue
        SetOfText(
          Sub(txtInp, 1,       posEnd+lenEnd-1)) <<
          TxtSplitBy2Tag(Sub(txtInp, posEnd+lenEnd, lenTxt), tagIni, tagEnd),
      TRUE,                           // Inicia posicion >1, termina y sigue
        SetOfText(
          Sub(txtInp, 1,       posIni-1),
          Sub(txtInp, posIni,  posEnd+lenEnd-1)) <<
          TxtSplitBy2Tag(Sub(txtInp, posEnd+lenEnd, lenTxt), tagIni, tagEnd))
  })
};
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
dos tags de inicio y de fin incluyendo dichos tags al inicio y al final de
cada texto que enmarcan.
Los tags tagIni y tabEnd no han de ser nulos.
Tiene mas sentido cuando a cada tag de inicio le corresponde uno de final.
Es una funcion recursiva.
Si funciona correctamente si los tags inicial y final son iguales.
TxtSplitBy2Tag(aaa<::>bbb<--->ccc, <, >) -> [aaav, <::>, bbb, <--->, ccc].",
TxtSplitBy2Tag);
//////////////////////////////////////////////////////////////////////////////


//////////////////////////////////////////////////////////////////////////////
Set TxtTokenizer(Text txtInp, // Texto de entrada
                 Text tagBrk) // Tag por el que se corta
//////////////////////////////////////////////////////////////////////////////
{ Tokenizer(Replace(txtInp, tagBrk, Char(7)), Char(7)) };
//////////////////////////////////////////////////////////////////////////////
PutDescription(
"Retorna un conjunto de textos resultado de cortar el texto de entrada por un
unico tag tagBrk no incluyendo el tag tagBrk dentro de los textos.
Se soporta en la funcion Tol Tokenizer() que rompe por un unico caracter.
Usa como caracter interno de corte el 7 (bell), esperando que no aparezca.",
TxtTokenizer);
//////////////////////////////////////////////////////////////////////////////

Árbol de ficheros

Dct.Writer documenta programas Tol generado agendas para Html

  • make.tol proceso principal de documentación de programas Tol
  • tol directorios de código Tol
    • cmm funciones comunes
    • app funciones especificas de aplicacion
      • shi.tol sintaxis realzada de código Tol, Xml, Html, etc.
      • dtr.tol de árboles de ficheros para documentación
      • dct.tol de documentación de código en Html
    • inc.tol para la inclusion de ficheros Tol
  • dct donde se generan las agenda de post de documentación
  • arbol.html ejemplo de árbol para documentar codigo fuente
  • dct_writer.pdf documento resumen de funciones del programa

2015 asolver.com | Aviso legal | XHTML | Δ Θ Ξ | Creative Commons | Mapa y funciones del sitio

Tol