☕ Um Café no Bellacosa Mainframe
Gostou do conteúdo? Ajude a manter o café quente, o COBOL compilando e o mainframe acordado. 😄
☕ Pague um café ao Bellacosa

Translate

Mostrar mensagens com a etiqueta Recursividade. Mostrar todas as mensagens
Mostrar mensagens com a etiqueta Recursividade. Mostrar todas as mensagens

segunda-feira, 22 de janeiro de 2024

COBOL Recursivo: Quando o Padawan Descobre que um Programa Pode Invocar a Si Mesmo

 

Bellacosa Mainframe apresenta um programa cobol recursivo

COBOL Recursivo: Quando o Padawan Descobre que um Programa Pode Invocar a Si Mesmo

O Poder Proibido do CALL Infinito na Galáxia IBM Z

Por Bellacosa Mainframe

"O medo leva ao ABEND. O ABEND leva ao dump. O dump leva ao sofrimento."

— Mestre Sysprog Yoda/390

Durante muitos anos, programadores COBOL cresceram acreditando em uma verdade absoluta:

"Programa COBOL não faz recursão."

Era praticamente um dogma do templo Jedi dos mainframes.

E, honestamente?

Durante décadas isso foi quase verdade.

A maioria dos sistemas bancários, seguradoras, governo e processamento batch nunca precisou de algoritmos recursivos.

Mas então surgiram:

  • XML

  • JSON

  • árvores hierárquicas

  • parsers

  • estruturas dinâmicas

  • APIs modernas

  • integração com Java

  • serviços z/OS Connect

E um dia o jovem Padawan perguntou:

"Mestre Bellacosa...

Posso fazer um programa COBOL chamar ele mesmo?"

A resposta é:

Sim.

Mas como todo poder da Força, existe um preço.


O que é Recursividade?

Recursão significa:

Um procedimento invoca ele próprio.

Exemplo clássico:

Calcular fatorial.

5! = 5 × 4 × 3 × 2 × 1

Matematicamente:

Fatorial(n)

se n=1 retorna 1

senão

n * Fatorial(n-1)

Exemplo:

F(5)

5 × F(4)

5 × 4 × F(3)

5 × 4 × 3 × F(2)

5 × 4 × 3 × 2 × F(1)

120

É uma técnica extremamente elegante.


COBOL Sempre Teve Recursão?

Não.

Historicamente COBOL nasceu em 1959.

E sua filosofia era:

Processamento comercial.

Arquivos.

Registros.

Batch.

Volumes enormes.

Não havia necessidade prática.

Durante décadas COBOL assumia:

Programa residente

Uma única Working Storage

Compartilhada

Exemplo:

WORKING-STORAGE SECTION.

01 CONTADOR PIC 9(5).

Só existe uma instância.

Todo mundo usa a mesma.

Problema:

Programa chama ele mesmo.

Segunda chamada sobrescreve variáveis.

Primeira execução quebra.

Caos.


Quando Surgiu?

IBM Enterprise COBOL começou suportar adequadamente recursão através da opção:

RECURSIVE

ou

RENT

Dependendo da geração do compilador.

Hoje encontramos suporte em:

Enterprise COBOL 4

Enterprise COBOL 5

Enterprise COBOL 6.x

COBOL 6.3

COBOL 6.4

COBOL 6.5

Totalmente suportado.

Inclusive no IBM z17.


Como Declarar um Programa Recursivo

No cabeçalho:

IDENTIFICATION DIVISION.
PROGRAM-ID. FATORIAL RECURSIVE.

ou

PROGRAM-ID. FATORIAL.

RECURSIVE.

Depende do compilador.


Exemplo Completo

Passo 1

Definir LINKAGE

LINKAGE SECTION.


01 LK-NUMERO.
   PIC 9(4).

01 LK-RESULTADO.
   PIC 9(10).

Passo 2

Procedure Division

PROCEDURE DIVISION USING
          LK-NUMERO
          LK-RESULTADO.

Passo 3

Caso base

IF LK-NUMERO <= 1

   MOVE 1 TO LK-RESULTADO

ELSE

...

Passo 4

Criar variável local

LOCAL-STORAGE SECTION.


01 WS-TEMP.
   PIC 9(10).

01 WS-N.
   PIC 9(4).

Local Storage é fundamental.

Já veremos por quê.


Passo 5

Preparar próxima chamada

COMPUTE WS-N = LK-NUMERO -1

Passo 6

Invocar a si mesmo

CALL 'FATORIAL'

USING

WS-N
WS-TEMP

Passo 7

Calcular

COMPUTE LK-RESULTADO =
        LK-NUMERO * WS-TEMP

Fim.


Programa Completo

IDENTIFICATION DIVISION.
PROGRAM-ID. FATORIAL RECURSIVE.

DATA DIVISION.


LOCAL-STORAGE SECTION.


01 WS-N.
   PIC 9(4).

01 WS-TEMP.
   PIC 9(10).


LINKAGE SECTION.


01 LK-NUMERO.
   PIC 9(4).

01 LK-RESULTADO.
   PIC 9(10).


PROCEDURE DIVISION USING
        LK-NUMERO
        LK-RESULTADO.


IF LK-NUMERO <= 1

   MOVE 1 TO LK-RESULTADO

ELSE

   COMPUTE WS-N =
           LK-NUMERO -1


   CALL 'FATORIAL'

   USING

      WS-N
      WS-TEMP


   COMPUTE LK-RESULTADO =
           LK-NUMERO * WS-TEMP

END-IF.


GOBACK.

O que Acontece na Memória?

Aqui mora a magia.

Imagine:

FATORIAL(5)

Stack:

Frame 1
n=5

Chama:

Frame 2
n=4

Depois:

Frame 3
n=3

Depois:

Frame 4
n=2

Depois:

Frame 5
n=1

Retorno:

Frame 5 → 1

Frame 4 → 2

Frame 3 → 6

Frame 2 →24

Frame 1 →120


Visualmente

STACK



F(5)

F(4)

F(3)

F(2)

F(1)

Depois:

POP


F(1)


F(2)


F(3)


F(4)


F(5)

O Papel da LOCAL-STORAGE

Muitos Padawans cometem um erro fatal.

Usar:

WORKING-STORAGE

Exemplo:

01 WS-N.

Errado.

Por quê?

Porque Working Storage é única.

Compartilhada.

Exemplo:

Primeira chamada

WS-N=5

Segunda

WS-N=4

Terceira

WS-N=3

Sobrescreve.

Tudo quebra.


LOCAL-STORAGE

Cria uma cópia nova.

Para cada chamada.

Exemplo:

Frame 1

WS-N=5

Frame 2

WS-N=4

Frame 3

WS-N=3

Independentes.


Como o Compilador Faz Isso?

Ele cria activation records.

Também chamados:

Stack frames

Contém:

Variáveis locais

Endereço retorno

Parâmetros

Estado execução

Exatamente igual:

C

C++

Java

Pascal


CALL Estático

Mais eficiente.

CALL 'FATORIAL'

Resolvido no linkedit.

Menos overhead.


CALL Dinâmico

MOVE 'FATORIAL'

TO WS-PGM


CALL WS-PGM

Mais flexível.

Menos rápido.


Existe Limite?

Sim.

STACK.

Região LE.

Memory limits.

Exemplo:

F(1000000)

Boom.

SOC1

SOC4

S878

S80A

Dependendo ambiente.


Como Evitar?

Caso base.

Sempre.

Sempre.

Sempre.

Exemplo ruim:

CALL FATORIAL


CALL FATORIAL


CALL FATORIAL

Nunca termina.


Cuidados Importantes

1 Não usar Working Storage

Errado.


2 Ter condição parada

Obrigatório.


3 Validar entrada

Exemplo:

IF NUMERO < 0

Fatorial negativo?

Não faz sentido.


4 Cuidado com profundidade

100 níveis

Ok.

500

Talvez.

10000

Perigoso.


5 Testar LE Runtime

HEAP

STACK

ALL31

Importante.


Performance

Aqui muitos ficam decepcionados.

Recursão é elegante.

Mas nem sempre rápida.

Cada chamada cria:

Frame

Parâmetros

Contexto

Retorno

Overhead.


Loop tradicional:

PERFORM


UNTIL

Quase sempre vence.


Exemplo

Fatorial iterativo.

MOVE 1 TO WS-TOTAL


PERFORM VARYING I


FROM 1


BY 1


UNTIL I > N


MULTIPLY I


BY WS-TOTAL


END-PERFORM

Muito eficiente.


Quando Vale a Pena?

Árvores.

XML.

JSON.

DOM.

Grafos.

Estruturas hierárquicas.

Menus.

Organogramas.

Filesystem.

Dependências.


Exemplo XML

empresa


 departamento


   funcionario


 departamento


   funcionario

Percorrer árvore.

Recursão fica linda.


Segurança

Sim.

Existe aspecto de segurança.

Ataque:

Stack exhaustion.

Negação de serviço.

DoS.

Programa recebe:

99999999

Explode stack.


Proteção:

IF NIVEL > 1000

DISPLAY "ERRO"

STOP RUN

Debug

Debug recursivo é divertido.

E assustador.

Ferramentas:

IBM Debug Tool

Fault Analyzer

Abend Aid

Mostram:

Call Stack

Frame atual

Parâmetros

Muito útil.


Curiosidades

Poucos sistemas bancários usam recursão pesada.

COBOL nasceu para processamento sequencial.

Por isso muitos programadores veteranos passam décadas sem escrever uma única rotina recursiva.


Outra curiosidade:

COBOL OO suporta métodos recursivos naturalmente.

INVOKE SELF

Também funciona.


Recursão de Cauda (Tail Recursion)

Alguns compiladores modernos fazem otimizações.

Mas COBOL IBM geralmente não realiza Tail Call Optimization de forma agressiva como linguagens funcionais.

Logo:

RETURN F(N-1)

Ainda pode consumir stack.

Não confie nisso.


Padrão Recomendado pelo Mestre Bellacosa

Para o jovem Padawan COBOL, eu costumo ensinar uma regra bastante prática:

Use recursão apenas quando ela deixar a solução mais clara do que um PERFORM VARYING.

Se a lógica for:

  • Fatorial

  • Somatório

  • Contador

Prefira iteração.

Se a lógica envolver:

  • Árvores

  • XML

  • JSON aninhado

  • Catálogos IMS

  • Dependências complexas

  • Estruturas organizacionais

  • Menus multiníveis

Então a recursividade torna-se uma excelente aliada.


Exemplo pratico de recursividade

Veja uma algoritmo em arvore B (B-Tree) search

https://eljefemidnightlunch.blogspot.com/2023/10/cobol-recursivo-sem-misterios.html


Considerações Finais

A recursão em COBOL é quase como encontrar um antigo holocron escondido nos corredores de um datacenter IBM Z.

Muitos veteranos nunca precisaram utilizá-la. Outros a evitam por receio de consumir stack, degradar performance ou provocar abends difíceis de diagnosticar.

No entanto, compreender programas recursivos amplia significativamente o repertório técnico de um desenvolvedor COBOL moderno. Em um mundo onde o mainframe conversa diariamente com APIs REST, processa documentos JSON complexos, integra-se com microsserviços e participa de arquiteturas híbridas, dominar recursividade deixa de ser apenas curiosidade acadêmica e passa a ser uma habilidade estratégica.

O verdadeiro Padawan não utiliza recursão para demonstrar inteligência. Ele a utiliza porque compreende profundamente o problema, conhece os limites da memória, respeita a pilha de execução do Language Environment, escolhe LOCAL-STORAGE sabiamente e sabe exatamente quando um simples PERFORM VARYING é a solução mais elegante.

E essa talvez seja a maior lição do COBOL recursivo:

Nem todo poder disponível deve ser usado. Mas todo poder disponível deve ser compreendido.

No templo Bellacosa Mainframe, conhecer a recursividade significa possuir mais uma ferramenta no cinto utilitário do Sysprog Jedi, pronta para ser acionada quando a missão exigir atravessar estruturas tão profundas quanto os corredores infinitos de uma galáxia IBM Z em plena era do z17.


quarta-feira, 25 de outubro de 2023

COBOL Recursivo sem Mistérios

 

Bellacosa Mainframe dicas e pratica em cobol mainframe recursivo

☕ Um Café no Bellacosa Mainframe

COBOL Recursivo sem Mistérios

Como Programar Funções Recursivas e Percorrer Árvores B como um Oficial da Frota Estelar

"A maioria dos programadores COBOL passa décadas escrevendo programas sem nunca utilizar recursividade. Não porque ela não exista. Mas porque o universo do processamento batch sempre favoreceu algoritmos iterativos. Entretanto, quando você entra no mundo de compiladores, parsers, XML, JSON, árvores de decisão, estruturas hierárquicas e inteligência artificial, descobrirá que existe uma arma secreta escondida dentro do Enterprise COBOL."

Prepare seu café.

Hoje o Capitão Kirk autorizou acesso aos bancos de dados mais profundos da USS Enterprise.

Vamos explorar uma tecnologia que muitos acreditam que COBOL "não possui".

Possui.

E muito bem.


O mito

Existe uma frase repetida há décadas:

"COBOL não suporta recursividade."

Isso era verdade...

...há muitos anos.

Desde o Enterprise COBOL moderno, programas podem chamar a si próprios.

Basta utilizar as opções corretas do compilador.

E entender o que realmente acontece na memória.


O que é recursividade?

Recursividade é quando um programa chama...

...ele mesmo.

Exemplo extremamente simples.

Imagine contar regressivamente.

5
4
3
2
1
Fim

Ao invés de fazer:

PERFORM VARYING

fazemos

CONTAR(5)

↓

CONTAR(4)

↓

CONTAR(3)

↓

CONTAR(2)

↓

CONTAR(1)

Cada chamada cria uma nova execução independente.


Pensando como Spock

Spock não resolveria um problema inteiro.

Ele dividiria.

Sempre.

Existe solução?

↓

Resolva um pedaço

↓

O restante é igual

↓

Chame novamente

Isso é exatamente recursividade.


Como o COBOL consegue fazer isso?

Cada chamada cria uma nova área de trabalho.

Ela contém:

  • variáveis locais

  • parâmetros

  • ponteiros

  • retorno

Tudo fica armazenado na pilha (Stack).

Visualmente.

MAIN

↓

PROGRAMA

↓

PROGRAMA

↓

PROGRAMA

↓

PROGRAMA

Cada nível ocupa memória.


Por isso existe um risco

Se esquecer a condição de parada...

Programa

↓

Programa

↓

Programa

↓

Programa

↓

Programa

↓

Programa

↓

Programa

Nunca termina.

Resultado:

Stack Overflow

Ou

S878

S80A

Storage Exhausted

Dependendo do ambiente.


A regra número 1

Toda função recursiva precisa possuir uma condição de parada.

Sempre.

Exemplo.

IF N = ZERO
    EXIT
END-IF

Sem isso...

adeus memória.


Ativando recursividade

No Enterprise COBOL normalmente utiliza-se

RECURSIVE

na identificação do programa.

IDENTIFICATION DIVISION.

PROGRAM-ID. TREESEARCH
    RECURSIVE.

ou opção equivalente do compilador dependendo da versão.

Outra prática comum é utilizar:

RENT

para permitir reentrância.


Reentrante x Recursivo

São conceitos diferentes.

Reentrante

→ vários usuários usam ao mesmo tempo.

Recursivo

→ o programa chama ele próprio.

Pode existir:

✔ Reentrante

sem ser

✔ Recursivo.


Quando utilizar?

Quando o problema possui natureza hierárquica.

Por exemplo.

Árvore.

XML.

JSON.

AST de compilador.

Pastas.

Menus.

Dependências.

Organogramas.

Genealogia.

Árvore de chamadas.


Imagine uma árvore B

Uma árvore B organiza registros.

             40

      20            60

   10   30      50     70

Encontrar um valor nela é extremamente elegante usando recursividade.


Estrutura lógica

Cada nó possui

Valor

Filho esquerdo

Filho direito

No COBOL real normalmente usamos tabelas e índices.

Exemplo didático.

NODE-ID

LEFT-CHILD

RIGHT-CHILD

Nossa missão

Encontrar

50

Algoritmo

Primeiro olhamos

40

50 é maior.

Então ignoramos todo lado esquerdo.

Seguimos para direita.

60

Agora

50 é menor.

Voltamos para esquerda.

Encontramos

50

Fim.


Em pseudocódigo

SEARCH(NODE)

IF NODE = NULL
    NÃO EXISTE

IF NODE = CHAVE
    ENCONTROU

SE CHAVE < NODE
    SEARCH(LEFT)

SENÃO
    SEARCH(RIGHT)

Perceba.

O algoritmo inteiro possui poucas linhas.

Porque ele reutiliza a própria lógica.


Exemplo COBOL simplificado

IDENTIFICATION DIVISION.
PROGRAM-ID. TREESEARCH RECURSIVE.

WORKING-STORAGE SECTION.

01 WS-KEY          PIC 9(4).

LINKAGE SECTION.

01 LK-NODE.
   05 LK-VALUE     PIC 9(4).
   05 LK-LEFT      POINTER.
   05 LK-RIGHT     POINTER.

PROCEDURE DIVISION USING LK-NODE.

    IF LK-NODE = NULL
        GOBACK
    END-IF

    IF WS-KEY = LK-VALUE
        DISPLAY "ENCONTRADO"
        GOBACK
    END-IF

    IF WS-KEY < LK-VALUE
        CALL "TREESEARCH"
             USING LK-LEFT
    ELSE
        CALL "TREESEARCH"
             USING LK-RIGHT
    END-IF.

    GOBACK.

Este exemplo é conceitual. Em aplicações reais, árvores costumam ser representadas por tabelas indexadas, estruturas dinâmicas com ALLOCATE/FREE (quando suportado) ou áreas obtidas por serviços do sistema.


Observe a mágica

O programa nunca pergunta

Estou no nível 2?

Estou no nível 5?

Estou no nível 30?

Ele simplesmente chama ele mesmo.


Visualizando a pilha

SEARCH(40)

↓

SEARCH(60)

↓

SEARCH(50)

↓

Encontrado

Depois começa retornar.

SEARCH(50)

↓

SEARCH(60)

↓

SEARCH(40)

↓

MAIN

É literalmente uma subida e descida.


O retorno automático

Cada chamada lembra onde parou.

Imagine.

A chama B

↓

B chama C

↓

C chama D

Quando D termina.

Volta para C.

Depois B.

Depois A.

Sem que você precise controlar isso.


Onde COBOL utiliza isso na prática?

Mais do que muitos imaginam.

Ferramentas IBM fazem uso intenso.

Compiladores COBOL.

Parser SQL.

Parser XML.

JSON Parser.

XPath.

XSD.

Analisadores sintáticos.

Motores de regras.


Árvore B em bancos

Db2 utiliza árvores B (B-Trees).

Quando fazemos

SELECT

WHERE CPF

O banco NÃO lê milhões de registros.

Ele navega pela árvore.

Raiz

↓

Nó

↓

Folha

Pouquíssimos acessos.


Curiosidade

Quando você cria

CREATE INDEX

Na prática.

Está construindo uma enorme árvore balanceada.


Então...

Todo programador COBOL usa árvore B.

Mesmo sem perceber.


Mas...

Devemos escrever árvore recursiva sempre?

Não.

Existe um preço.


CPU

Cada chamada possui custo.

Salvar registradores

↓

Criar stack frame

↓

Passar parâmetros

↓

Retornar

Tudo isso consome CPU.


Memória

Cada chamada cria.

Variáveis

Endereço retorno

Parâmetros

Estado

Imagine 100.000 níveis.

Pode explodir.


Comparando

Iterativo

WHILE

Consome

CPU menor

Memória fixa

Recursivo

CPU maior

Stack crescente

Então por que usar?

Porque alguns problemas ficam absurdamente mais simples.

Exemplo.

Árvore.

Iterativo

300 linhas

Recursivo

40 linhas

Mais fácil.

Mais elegante.

Menos bugs.


Quando evitar?

Processamento sequencial.

Leitura VSAM.

Arquivo QSAM.

Loops simples.

Relatórios.

Batch tradicional.

Nestes casos.

PERFORM VARYING

vence.


Tail Recursion

Existe uma otimização famosa.

Tail Recursion.

Função termina chamando ela mesma.

Alguns compiladores eliminam o crescimento da pilha.

Infelizmente.

Nem todo compilador COBOL faz isso.

Portanto.

Nunca conte com essa otimização.


Cuidado com milhões de chamadas

Imagine uma árvore degenerada.

10

 \

 20

   \

   30

     \

     40

Ela parece uma lista.

A recursividade fará milhares de chamadas.

Ruim.

Árvores balanceadas evitam isso.


B-Tree resolve exatamente este problema

Ela mantém altura pequena.

Mesmo com milhões de registros.

É justamente por isso que bancos usam B-Tree.

Não Binary Tree simples.


Dica de ouro

Nunca escreva recursividade sem antes responder:

Qual é minha condição de parada?

Se não conseguir responder.

Ainda não terminou o algoritmo.


Outra dica

Desenhe.

Sempre.

Árvores ficam muito mais fáceis no papel.


Debug

Durante testes faça:

DISPLAY

Mostrando o nível.

DISPLAY "LEVEL=" WS-NIVEL

Assim você visualiza a profundidade.


Performance em Mainframe

No IBM Z.

CPU é dinheiro.

Cada microssegundo importa.

Por isso.

Recursividade costuma aparecer mais em:

  • middleware

  • compiladores

  • parsers

  • XML

  • JSON

  • IA

  • engines

Do que em batch financeiro.


Curiosidade histórica

Nos anos 70.

Poucos compiladores COBOL aceitavam recursividade.

A memória era extremamente cara.

Muitas máquinas tinham poucos megabytes.

Era impensável desperdiçar stack.

Hoje.

Servidores IBM Z possuem centenas de gigabytes.

O cenário mudou.


Boas práticas

✔ Sempre tenha condição de parada clara.

✔ Documente a lógica antes de codificar.

✔ Prefira árvores balanceadas.

✔ Limite profundidade quando possível.

✔ Evite variáveis globais compartilhadas.

✔ Teste casos extremos.

✔ Monitore consumo de CPU e memória.

✔ Utilize recursividade apenas quando ela realmente simplifica o problema.

✔ Faça revisão de código focando em chamadas recursivas.

✔ Meça desempenho antes de concluir que a solução é "rápida".


Armadilhas comuns

❌ Esquecer a condição de parada.

❌ Modificar dados globais inesperadamente.

❌ Assumir que toda árvore é balanceada.

❌ Ignorar consumo de stack.

❌ Trocar elegância por complexidade desnecessária.

❌ Usar recursividade onde um PERFORM VARYING resolveria de forma mais simples.


Recursividade e Enterprise COBOL

As versões modernas do IBM Enterprise COBOL oferecem suporte a programas recursivos, mas é importante observar alguns detalhes:

  • Declare o programa como RECURSIVE quando necessário.

  • Utilize opções de compilação adequadas ao ambiente, frequentemente combinadas com RENT em aplicações compartilhadas.

  • Consulte sempre o padrão adotado pela sua empresa e a documentação da versão do compilador em uso, pois políticas de compilação variam entre instalações.

Em ambientes CICS, IMS ou aplicações de alta concorrência, também é essencial compreender os conceitos de reentrância, armazenamento automático e áreas de trabalho para evitar efeitos colaterais entre execuções simultâneas.


Missão para o Padawan COBOL

Depois de dominar este artigo, experimente implementar os seguintes desafios:

  1. Fatorial usando recursividade.

  2. Sequência de Fibonacci (comparando desempenho com versão iterativa).

  3. Percorrer uma árvore binária em ordem (in-order).

  4. Percorrer uma árvore em pré-ordem (pre-order).

  5. Percorrer uma árvore em pós-ordem (post-order).

  6. Simular um índice de clientes usando uma árvore binária simples.

  7. Comparar o tempo de busca entre uma tabela sequencial e uma árvore.

  8. Criar um visualizador com DISPLAY mostrando o nível de cada chamada recursiva.

Cada exercício ajudará você a entender não apenas como a recursividade funciona, mas quando ela é realmente a melhor ferramenta.

Conclusão — O Holodeck da Recursividade

Existe uma lição que diferencia um programador comum de um verdadeiro oficial da Frota Estelar.

O iniciante procura resolver problemas escrevendo mais código.

O engenheiro experiente procura resolver problemas encontrando a estrutura correta.

A recursividade é exatamente isso: uma mudança de perspectiva. Em vez de atacar um problema gigantesco de uma única vez, você o divide em pequenas partes idênticas, permitindo que o próprio algoritmo repita a solução até alcançar a condição de parada.

No universo do COBOL, ela não substitui os tradicionais PERFORM VARYING, nem foi criada para processar milhões de registros sequenciais de um batch financeiro. Seu verdadeiro poder aparece quando trabalhamos com estruturas hierárquicas: árvores B, XML, JSON, compiladores, interpretadores, mecanismos de regras, grafos e diversos algoritmos modernos que fazem parte da computação atual.

Como diria o Sr. Spock:

"A solução mais elegante normalmente é aquela que respeita a estrutura natural do problema."

Quando você compreender essa filosofia, deixará de enxergar a recursividade como um truque de linguagem e passará a vê-la como uma ferramenta de modelagem.

E esse é um dos momentos em que um Padawan COBOL começa a trilhar o caminho para se tornar um verdadeiro Mestre do Mainframe.


Vagner Renato Bellacosa, IBM Champion e especialista em IBM Mainframe
IBM Z17 SYSTEM ONLINE
Sobre o autor

Vagner Renato Bellacosa

IBM Champion 2026 • Especialista em IBM Mainframe

Vagner Renato Bellacosa trabalha com IBM Mainframe desde 1988 , é IBM Champion e especialista em COBOL, CICS, Db2, z/OS e IBM Z. Compartilha experiências profissionais, conhecimento técnico, história da computação e práticas do universo mainframe para aproximar novas gerações das tecnologias que sustentam empresas, bancos e governos ao redor do mundo.

IBM Champion IBM Z COBOL CICS Db2 z/OS Mainframe desde 1988
GitHub LinkedIn
Inicializando conteúdo...