Words (1): Uma função para contar a quantidade de palavras numa string

Em outras linguagens, como Java ou Javascript, é possível fazer um split e transformar uma string num array em que cada ocorrência corresponda a uma palavra da string original.

Num primeiro momento, podemos imaginar que o COBOL faria a mesma coisa com o comando UNSTRING, mas existe uma diferença essencial: enquanto Java, Javascript e outras linguagens trabalham com arrays dinâmicos (arrays cuja quantidade de ocorrências se pode definir em tempo de execução), no COBOL temos que estabelecer uma quantidade máxima de palavras para que o UNSTRING funcione do jeito que queremos. Algo como:

UNSTRING UMA-STRING-QUALQUER
   DELIMITED BY ALL SPACES
   INTO PALAVRA(1)
        PALAVRA(2)
        PALAVRA(3)
        PALAVRA(4)

Se no comando acima, UMA-STRING-QUALQUER tivesse cinco palavras, a quinta seria perdida. Em um programa real…

identification division.
program-id. gtc034.

data division.
working-storage section.
01 uma-string-qualquer pic x(080) 
    value "perform paragrafo varying indice from 1 by 1".
01 palavra pic x(010) occurs 4.

procedure division.
    unstring uma-string-qualquer
        delimited by all spaces
        into palavra(1)
             palavra(2)
             palavra(3)
             palavra(4)

    display "palavra(1)=" palavra(1)
    display "palavra(2)=" palavra(2)
    display "palavra(3)=" palavra(3)
    display "palavra(4)=" palavra(4)

    stop run.

…o resultado da execução seria:

 > Executing task in folder coblab: gtc034 < 
 palavra(1)=perform   
 palavra(2)=paragrafo 
 palavra(3)=varying   
 palavra(4)=indice    

Felizmente usando alguns recursos do COBOL 2002 é possível criar funções que contornam essa limitação. E esses recursos estão disponíveis na maior parte dos compiladores atuais.

Este artigo faz parte de uma série de três onde pretendo mostrar como criei essas funções.

Criando a função getWordCount

A função abaixo foi codificada e testada no GnuCOBOL 3.1.0, mas com poucas alterações pode ser implementada em quase todos os compiladores que incorporaram os recursos do COBOL 2002:

identification division.
function-id.    getWordCount.

environment division.
configuration section.
repository.
    function all intrinsic.

data division.
working-storage section.
01 subscript        binary-short unsigned value zeros.
01 stringState      pic 9(001)  value zeros.
    88 wasSpace                 value 1 false 0.

linkage section.
01 fullString       pic x any length.
01 wordsCounted     binary-short unsigned.

procedure division using fullString returning wordsCounted.
0-main.

    move zeros to subscript
    move zeros to stringState
    move zeros to wordsCounted

    perform varying subscript from 1 by 1 until subscript > length(fullString)
        if fullString(subscript:1) = spaces 
            set wasSpace to true
        else    
            if subscript = 1
                add 1 to wordsCounted
            else    
                if wasSpace 
                    add 1 to wordsCounted
                    set wasSpace to false
                end-if
            end-if
        end-if
    end-perform

    goback.

end function getWordCount.

Criando a variável fullString na linkage section com pic x any length a função poderá receber strings de qualquer tamanho. Quem vai definir esse tamanho é o programa chamador.

Outro ponto importante é que essa versão mais recente do GnuCOBOL não permite ainda declarar a cláusula “is initial” no parágrafo function-id da identification division. Por isso, coloquei os três comandos “move zero” no início da procedure, garantindo que as variáveis serão sempre inicializadas se o programa chamador executar a função mais de uma vez.

Testando a função

Codificando um programa chamador…

identification division.
program-id. gtc035.

environment division.
configuration section.
repository.
    function getWordCount.

data division.
working-storage section.
01 uma-string-qualquer pic x(080) 
    value "perform paragrafo varying indice from 1 by 1".

procedure division.
inicio.

    display "O conteudo da string possui " 
             getWordCount(uma-string-qualquer) 
             " palavras"
    stop run.

…temos o seguinte resultado:

 > Executing task in folder coblab: gtc035 < 
 O conteudo da string possui 00008 palavras

No próximo artigo…

…vamos mostrar uma função que também em COBOL que usa essa getWordCount para recuperar uma palavra dentro da string.


Deixe um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *