Logo Passei Direto
Buscar
Material
páginas com resultados encontrados.
páginas com resultados encontrados.
left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

left-side-bubbles-backgroundright-side-bubbles-background

Crie sua conta grátis para liberar esse material. 🤩

Já tem uma conta?

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

Prévia do material em texto

Pensamento computacional para sistemas 
de larga escala
Apresentação
A partir da década de 1960, houve a popularização dos computadores como ferramentas para 
automatização de processos, pesquisa científica e automação. O software até então não tinha um 
papel de destaque, sendo toda a atenção destinada ao desenvolvimento do hardware. Com isso, 
novas demandas surgiram, com a necessidade de sistemas mais aplicados.
A partir de então, em sistemas de larga escala, de folhas de pagamento até lançamentos de 
foguetes, o software começou a tomar conta do mercado. Com o aumento da complexidade dos 
sistemas e a falta de ferramentas adequadas para a construção, relatos de problemas relacionados 
ao software tornaram-se comuns. Erros que prejudicam a confiabilidade diminuíram a produtividade 
e, às vezes, representavam riscos de acidentes.
Nesta Unidade de Aprendizagem, você vai saber como o Pensamento Computacional está 
relacionado com a construção de sistemas de larga escala e como surgiu a necessidade de definir 
princípios e padrões da engenharia de software para essa construção. Também serão discutidos as 
origens da engenharia de software e alguns tópicos sobre as dificuldades existentes no 
desenvolvimento de aplicações reais. 
Bons estudos.
Ao final desta Unidade de Aprendizagem, você deve apresentar os seguintes aprendizados:
Descrever a relação entre engenharia de software e Pensamento Computacional.•
Listar princípios e padrões relevantes para a engenharia de software.•
Determinar as dificuldades existentes no desenvolvimento de aplicações reais.•
Desafio
Princípios de projeto são importantes ferramentas da engenharia de software, as quais contêm um 
conjunto de sugestões e parâmetros para favorecer a manutenção e a evolução da aplicação. 
Mesmo que o projeto seja inicialmente pequeno, criá-lo de forma a reduzir a complexidade no 
momento de um possível aumento de escala diminui custos com o projeto e evita muitos problemas 
para a equipe de desenvolvimento. Diversos princípios são conhecidos, como os princípios DRY 
(Don't repeat yourself), KISS (Keep It Simple, Stupid), YAGNI (You aren't gonna need it) e SOLID (um 
acrônimo que une cinco regras de escrita, cada um representado por uma letra, que, ao final, 
formam a palavra "sólido", em inglês).
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para 
acessar.
Considerando o trecho apresentado e a descrição do problema, qual princípio SOLID está sendo 
violado? Que alteração você sugere para adequar a funcionalidade?
Infográfico
Quanto maior a escala do sistema, mais se demanda o emprego de processos sistêmicos e 
metodologias para sua construção, manutenção e evolução. Nesse ponto, a engenharia de software 
tem por função recomendar e empregar princípios comuns às engenharias na construção de 
software.
Diversos autores definiram princípios e padrões amplamente discutidos e difundidos por equipes 
de desenvolvimento, como os sete princípios de Pressman, os princípios SOLID, padrões GOF e 
padrões GRASP.
Neste Infográfico, você vai conhecer os princípios SOLID para construção de software.
Aponte a câmera para o 
código e acesse o link do 
conteúdo ou clique no 
código para acessar.
Conteúdo do livro
Desde sua proposição na década de 1960, a engenharia de software tem se empenhado na 
definição de processos, princípios e padrões para construção de software de qualidade, garantindo 
confiabilidade, produtividade e manutenção em sistemas de larga escala.
Engenharia de software proporciona disciplina e procedimentos sistemáticos e quantificáveis, com 
foco no desenvolvimento, na usabilidade, na manutenção e na evolução de sistemas de software. 
Resumindo, a engenharia de software tem por função recomendar e empregar princípios comuns às 
engenharias na construção de software.
No capítulo Pensamento Computacional para sistemas de larga escala, base teórica desta Unidade 
de Aprendizagem, você vai conhecer um pouco mais sobre as origens da engenharia de software e 
como a área se relaciona com o Pensamento Computacional, bem como os problemas enfrentados 
na construção de software e como a definição de princípios e padrões pode afetá-los.
Boa leitura.
PENSAMENTO 
COMPUTACIONAL 
OBJETIVOS DE APRENDIZAGEM
 > Descrever a relação entre engenharia de software e pensamento com-
putacional.
 > Reconhecer princípios e padrões relevantes para a engenharia de software.
 > Determinar as dificuldades existentes no desenvolvimento de aplicações 
reais.
Introdução
Dos primórdios da computação, desde a tábua de calcular, até os grandes 
mainframes IBM, o hardware sempre foi o grande destaque. A história, po-
rém, teve uma reviravolta por volta dos anos 1960, de forma que, atualmente, 
empresas de diversos tamanhos são dependentes de sistemas de informação 
que auxiliam em tomadas de decisão, automatização e gestão. Sistemas de 
grande escala estão mais inseridos em nosso cotidiano do que conseguimos 
perceber, na análise do comportamento de um usuário nas redes sociais, no 
controle dos aparelhos de uma aeronave ou simplesmente para pedir uma 
refeição pelo smartphone.
Pensamento 
computacional 
para sistemas de 
larga escala
Marcelo da Silva dos Santos
Devido à importância do software atualmente, não é estranho que exista 
uma área da computação reservada à criação de estratégias para o desenvolvi-
mento de aplicações, principalmente aquelas de larga escala e complexidade. 
A engenharia de software se dedica à criação de metodologias quantificáveis 
e sistemáticas para desenvolvimento, gerência, manutenção e escalabilidade 
em sistemas de software. Ou seja, sua intenção é definir princípios e padrões 
da engenharia para desenvolvimento de software.
Neste capítulo, você vai conhecer a área de engenharia de software, com 
destaque para sua relação com o pensamento computacional. Também serão 
apresentados os princípios e padrões para o desenvolvimento de sistemas de 
larga escala e os desafios no desenvolvimento de aplicações.
Engenharia de software e pensamento 
computacional
A engenharia de software teve início em meados da década de 1960, após 
longos anos de hegemonia do hardware. Nas décadas que antecederam, 
grandes máquinas eram utilizadas para a validação de problemas científicos 
em universidades, algumas grandes empresas ou agências governamentais. 
O software não era relevante e essas grandes máquinas tinham pouco poder 
de processamento equiparado aos atuais computadores domésticos. Ainda 
assim, podiam calcular milhares de vezes mais rápido do que os melhores 
matemáticos do mundo (DENNING; TEDRE, 2019).
Pouco tempo depois, calcular não era mais suficiente, de modo que di-
ferentes aplicações começaram a surgir. De simuladores que desafiavam 
enxadristas até a implantação dos primeiros sistemas projetados para os 
hospitais norte-americanos (DENNING; TEDRE, 2019; ARREGUY-SENA, 1999), 
o software foi inserido em diversas áreas de conhecimento com a intenção 
de dar suporte à tomada de decisão, à pesquisa e ao lazer. Portanto, a aurora 
da computação moderna teve início com o hardware, mas o software logo 
ganhou território (DENNING; TEDRE, 2019).
Por consequência do aumento da demanda, a escala e a complexidade 
desses novos sistemas também sofreram impacto importante, ainda em um 
momento em que os processos de desenvolvimento eram relativamente 
imaturos. Garantir a qualidade da produção em grande escala (confiabilidade, 
usabilidade, segurança, entre outras características) era inviável, pois as 
ferramentas para desenvolvimento e gestão desenvolvidas até então não 
eram poderosas o suficiente para isso. Tal cenário levou ao aumento da 
Pensamento computacional para sistemas de larga escala2
descrença no software, devido a recorrentes perdas de prazo, orçamento 
elevado, falta de atendimento aos requisitos e manutenção inviável. De acordo 
com Valente (2020), a apreensão era tanta que esse período foi chamado de 
“crise do software”.
Tanta era a preocupação que,em 1968 e 1969, a Organização do Tratado 
do Atlântico Norte (OTAN) patrocinou duas reuniões para debater o assunto. 
O objetivo era discutir um problema crescente na computação, o software. 
Casos catastróficos, como o caso do lançamento da Mariner I, uma sonda 
interplanetária produzida pela National Aeronautics and Space Administration 
(NASA) destinada a fazer pesquisas aéreas de Marte, Mercúrio e Vênus e que 
perdeu o controle 293 segundos após a decolagem em virtude de um erro 
de programação mínimo (DENNING; TEDRE, 2019), reforçaram a importância 
da discussão.
A conferência, ocorrida na cidade de Garmisch (Alemanha), reuniu pes-
quisadores em busca de uma solução para a crise que havia se instaurado. 
Era consenso a necessidade que fosse definido com urgência um conjunto 
de princípios teóricos e práticos, um arcabouço de regras que direcionasse a 
construção de software consistentes e confiáveis. Assim, eles buscaram nas 
engenharias, área de conhecimento reconhecida em notáveis processos de 
construção em todas as subáreas que atuam, inspiração para essa nova área 
computacional, então batizada de engenharia de software.
Mais de meio século após sua criação, a aplicação do pensamento compu-
tacional aliado à rigidez formal da engenharia trouxe avanços em metodologias 
e técnicas de desenvolvimento consideravelmente notáveis. Princípios e 
padrões foram definidos e aplicados em sistemas de grande escala, de forma 
que favorecem a reutilização e a redução de tempo de produção. Frameworks 
e bibliotecas agilizam o trabalho, de forma que os desenvolvedores podem 
abstrair detalhes inerentes a processos comuns, como interfaces, bases e 
estruturas de dados, criptografia, etc. Também metodologias para teste e 
validação são utilizadas para garantir qualidade e eliminação de falhas, bem 
como para a manutenção e a evolução durante o passar do tempo.
Pensamento computacional em sistemas 
de larga escala
Como vimos anteriormente, desde sua origem, no interior das universidades, 
o pensamento computacional do início da era do computador era rico, mas 
fragmentado, e focava em fazer programas individuais funcionarem em má-
quinas específicas (DENNING; TEDRE, 2019). Muitos desses sistemas, como já 
Pensamento computacional para sistemas de larga escala 3
foi mencionado, eram relativamente pequenos comparados às aplicações 
dos dias atuais. E não estamos falando de grandes sistemas de informação: 
um aplicativo embarcado em seu celular já possui capacidade computacional 
superior à disponível naquela época. Grande parte daqueles programas era 
direcionada para a resolução de cálculos matemáticos complexos, que exigiam 
grande esforço dos matemáticos de então.
Atualmente, diversos segmentos têm empregado esforços para a cons-
trução de sistemas cada vez mais complexos e escaláveis, com inserção em 
diversas áreas do conhecimento, como ciência, pesquisa, gestão governa-
mental, esportes, medicina, entre outros ramos. 
Diferentemente dos primeiros anos do computador, quando o hardware 
reinava absoluto, com o passar do tempo, a demanda por software aumentou 
exponencialmente. Sistemas ampliaram sua escala de forma considerável, de 
modo que os sistemas, antes individuais e para uso específico, tornaram-se 
complexos, multitarefas e essenciais. Como exemplos, podemos citar o con-
trole de processos produtivos na indústria, em logística, na forma de controle 
de frota, em sistemas governamentais (eleições, impostos e serviços), nos 
negócios digitais, agindo de forma ubíqua, na forma de serviços baseados em 
perfis de comportamento dos consumidores, etc. Uma ampla variedade de 
sistemas também está embarcada em diversos equipamentos, como automó-
veis, aeronaves, satélites, usinas nucleares, etc. O pensamento computacional 
e a evolução das técnicas de construção de software proporcionaram solo 
fértil para pesquisas e descobertas recentes e para as que ainda estão por vir.
O termo computação ubíqua foi cunhado em 1991, por Mark Weiser, 
no artigo “O Computador para o século XXI”, no qual apresentava o 
conceito de dispositivos conectados em todos os lugares de forma imperceptível 
para o ser humano, de forma que acabaríamos por não notar sua influência em 
nosso cotidiano. Seu objetivo é oferecer serviços de forma “invisível”, de modo 
que os serviços são oferecidos e utilizados sem mesmo percebermos, baseado 
em perfis de comportamento do usuário e sua rotina.
Para isso, um perfil é criado utilizando as mais diversas fontes, como o 
aparelho celular (áudio, aplicativos, etc.), ou outras formas de acesso (smart TV, 
computador pessoal e dados de redes Wi-Fi públicas, etc.), criando o conceito de 
computação sensível ao contexto, ou seja, ajustando o serviço que é oferecido 
à situação e ao local onde o usuário se encontra. Por exemplo, oferecer um 
cupom de desconto para determinado produto ao identificar que o usuário está 
passando em frente à loja.
Pensamento computacional para sistemas de larga escala4
Mas o que mudou do momento que passamos das simples aplicações 
monotarefas para sistemas de complexos e multiusuários? Os pesquisado-
res e profissionais da computação também tiveram que se adaptar, visto 
que as habilidades e competências antes exigidas para um programa que 
não passava de mil linhas de codificação agora são outras, considerando 
construir um software com mais de um milhão de linhas (RILEY; HUNT, 2014). 
O trabalho antes realizado por um único programador agora exige trabalho em 
equipe. Os profissionais, antes solitários e escondidos nos datacenters, com 
o passar do tempo precisaram aprender a organizar e gerenciar equipes e a 
desenvolver metodologias para o desenvolvimento de software bem-sucedido 
(DENNING; TEDRE, 2019). E essa não é uma tarefa simples. Brooks (1986), um 
dos pesquisadores que definiu regras básicas de pensamento computacional, 
seguidas até hoje, concluiu que gerenciar a equipe é um desafio maior do que 
os problemas de tecnologia que a equipe precisará resolver.
Outro ponto de aprendizado é que existiria a necessidade de ferramentas 
próprias, diferentes das tradicionais, devido a diferenças essenciais entre 
software complexos e grandes sistemas físicos, como pontes, edifícios, aviões 
e navios: um erro em um único bit de código pode causar falha catastrófica, 
enquanto a perda de uma pequena lasca de material pode até desgastar a 
construção, mas dificilmente vai causar um colapso na estrutura (VALENTE, 
2020). Fez-se necessária, então, a definição de princípios e padrões próprios, 
que poderiam ser utilizados por engenheiros de software ou desenvolvedores 
em suas construções, de forma que eles aproveitassem experiências bem-
-sucedidas e evitassem recomeços a cada novo problema de projeto. 
Princípios e padrões para a engenharia de 
software
No primeiro momento, quando se fala em engenharia de software, logo se 
pensa em programação, mas a área de estudo envolve um universo mais amplo. 
Além das técnicas de programação, a engenharia de software se concentra em 
recomendar princípios e padrões da engenharia na construção de software, 
utilizando pensamento computacional e processos sistêmicos, de maneira 
disciplinada e quantificável, com a finalidade de construir, manter e evoluir 
sistemas de software. Software, portanto, não é apenas o arquivo executável 
final, pois inclui toda a documentação necessária (arquivos de configuração, 
manual de instalação e utilização) e o banco de dados.
Pensamento computacional para sistemas de larga escala 5
Para essa área de concentração, software consiste em uma coleção de 
requisitos, tanto não funcionais quanto funcionais, que atendam às necessi-
dades do cliente. No modelo do processo de desenvolvimento de software, 
o projeto é o primeiro estágio no processo de construção de software. Faz a 
ligação entre o projeto e a engenharia de requisitos, pois identifica os prin-
cipais componentes estruturais de um sistema e os relacionamentos entre 
eles (SOMMERVILLE, 2007).
O pensamento computacionalsugere soluções, como realizar a decom-
posição do problema, para que cada segmento do projeto seja implemen-
tado independentemente, e o uso de abstrações para criar representações 
simplificadas das entidades, reduzindo sua complexidade. Tais abstrações 
permitem interagir e utilizar a entidade abstraída, reduzindo a necessidade 
de dominar todas as minúcias envolvidas em sua implementação. São arte-
fatos oferecidos pelas linguagens de programação com os quais podemos 
representar as abstrações, como, por exemplo, métodos, classes, pacotes, 
pacotes, interfaces, bibliotecas, etc.
Porém, reduzir a complexidade do projeto não é um tema simples, con-
siderando que os sistemas modernos aumentam cada vez mais sua comple-
xidade. Segundo Wirth (2008), isso afeta a qualidade do produto e, muitas 
vezes, problemas de projeto são disfarçados pelo hardware, com o uso de 
processadores mais rápidos ou deficiências no design de dados ocultos pelo 
uso de dispositivos de armazenamento maiores. Um projeto bom e cuidadoso 
consome tempo e pode ter custo elevado, mas ainda é mais barato do que 
um software sem usabilidade e não confiável, levando em conta o custo de 
“manutenção” (WIRTH, 2008).
Pensando em incremento na qualidade, capacidade de identificar e pro-
jetar integrações com outros sistemas e recursos, expansões e possíveis 
incrementos de escala, é interessante conhecer e aplicar algumas práticas 
do pensamento computacional. Vejamos.
 � Princípios de projeto: descrições de habilidades e estratégias que os 
desenvolvedores seguem ao tomar decisões de design.
 � Padrões de projeto: descrições de situações comuns que um progra-
mador provavelmente encontrará. Eles oferecem orientação sobre 
como estruturar o programa ou sobre o processo de escrevê-lo, para 
obter melhores resultados.
Pensamento computacional para sistemas de larga escala6
Tanto os princípios quanto os padrões podem ser compreendidos como 
um conjunto de regras práticas ou de conselhos, mais úteis para aqueles 
com habilidades avançadas no desenvolvimento de sistemas. Aprender suas 
principais ferramentas e habilidades exige uma certa dose de atenção, per-
sistência e disciplina, e, como a maioria das competências que o ser humano 
desenvolve, também demanda bastante prática.
Princípios
Em termos gerais, princípios são conceitos ou valores que orientam a tomada 
de decisão. Assim, os princípios de projeto são recomendações concretas 
que desenvolvedores de software podem incorporar à forma de raciocínio e 
aos hábitos que os desenvolvedores de sistemas desenvolvem ao longo do 
tempo, ao construir sistemas de computação complexos (DENNING; TEDRE, 
2019). Eles representam diretrizes para garantir que um projeto atenda a 
determinadas propriedades e se aplicam a qualquer sistema de larga escala 
capaz de gerenciar grandes volumes de usuários e processos concomitan-
tes. Como exemplos práticos, podemos destacar os Princípios de Saltzer e 
Schroeder (1975) para proteção de informações e os princípios SOLID. Por sua 
extensão e complexidade, vamos conhecer resumidamente alguns conceitos 
sobre esses princípios.
Para auxiliar sua leitura, muitos dos princípios e padrões são voltados 
para o paradigma orientado a objetos. Sem estender os conceitos, 
abaixo são descritos alguns dos termos recorrentes em orientação a objetos e 
que não foram tratados diretamente no capítulo.
 � Classe abstrata: normalmente é formada por métodos abstratos. O método 
abstrato descreve somente a assinatura do método e, portanto, não con-
tém código interno (implementação do método). Esses métodos são imple-
mentados em suas classes derivadas concretas, em que são definidos seus 
comportamentos específicos. 
 � Classe concreta: possui atributos, métodos construtores e demais componen-
tes necessários, e pode ser instanciada, ou seja, permite a criação de objetos 
a partir dela. Classes concretas podem ser herdadas por outras classes.
 � Interface: utilizada para a definição de um modelo por meio da assinatura 
de métodos. Assim como na classe abstrata, a implementação desse método 
será realizada pelas classes que a herdarem. O uso de interfaces possibilita 
o polimorfismo.
Pensamento computacional para sistemas de larga escala 7
 � Acoplamento: é a medida de quanto dois ou mais módulos estão “amarrados”, 
ou seja, de quanto uma classe depende da outra para efetuar seu trabalho. 
O ideal é buscar o mais baixo acoplamento, em que cada uma depende de 
si mesma para executar as tarefas. Alto acoplamento existe, por exemplo, 
quando parte de um processo está em uma classe (ou módulo) e o restante 
está em outra (nenhuma das duas consegue entregar o resultado sozinha).
 � Coesão: um módulo coeso realiza uma única tarefa dentro de um procedimento 
de software, requerendo pouca ou nenhuma interação com procedimentos 
sendo realizados em outras partes de um programa. Uma classe não deve 
assumir responsabilidades que não são suas (Princípio da Responsabilidade 
Única).
Segundo Saltzer e Schroeder (1975), em um projeto de software, para ga-
rantir qualidade no quesito segurança da aplicação, o desenvolvedor deve ter 
em mente oito princípios fundamentais, de forma a evitar possíveis compro-
metimentos de informações confidenciais. Esses princípios são os seguintes.
1. Economia de mecanismos: o primeiro princípio diz respeito aos algo-
ritmos e métodos empregados na implementação da segurança, aqui 
chamados de mecanismos. Esses mecanismos devem ser, na medida 
do possível, simples e sucintos no tocante à codificação, facilitando 
sua leitura e minimizando a possibilidade de erros de codificação.
2. Bloquear acessos por padrão: sistemas devem, naturalmente, negar 
acessos a seus recursos, com a exceção de que o acesso tenha sido 
concedido de forma explícita. As funcionalidades de um sistema só 
poderão ser executadas se tiverem permissão para tal. Por exemplo, 
um sistema só deve receber acesso à internet permitido no momento 
de aplicar uma atualização.
3. Mediação completa: qualquer acesso solicitado, mesmo para recursos 
do sistema operacional, deve ser verificado (mediação). Dessa forma, 
para cada solicitação, aproveita-se para verificar se existe autorização 
para tal acesso.
4. Padrão aberto: a segurança do sistema não deve depender da ignorância 
dos invasores sobre como é construída sua aplicação. O sistema deve se 
respaldar em mecanismos de segurança, como senhas e encriptação por 
chaves, e não em esconder a arquitetura ou os componentes utilizados.
5. Separação de privilégios: evite criar perfis que tenham grandes níveis 
de acesso. Tente separar as ações de forma a gerenciar permissões 
somente das partes necessárias a cada atividade.
Pensamento computacional para sistemas de larga escala8
6. Menor privilégio: apenas permissões estritamente necessárias devem 
ser consentidas, e cada perfil deve ter as permissões necessárias para 
executar sua tarefa, nada mais.
7. Menor número de mecanismos comuns (compartilhados): deve-se evitar 
o compartilhamento de recursos para evitar acessos indesejados. Um 
mecanismo (recurso) comum contém informação vinculada e, caso 
alguém o acesse, pode tentar influenciar no comportamento de outros 
que dependem dele. Por exemplo, uma base de dados de usuários 
utilizada para autenticação por diversas aplicações. Uma solução seria 
cada sistema ter sua própria base para controle de acessos, mesmo 
com informações replicadas, o que pode incrementar a segurança.
8. Aceitação psicológica: princípio também conhecido como psicologi-
camente aceitável, diz que as regras devem ser razoáveis, pois, se a 
interação com o usuário não for intuitiva, o mecanismo de segurança 
até pode ser eficaz, mas tende a falhar porque não será utilizado da 
maneira correta e seguido com o rigor esperado.
Outro conjunto de princípios de destaque na engenharia de software 
é o que resultou do trabalho de Robert Martin, em um artigo chamado de 
“Principles of Object Oriented Design” e expandido em outras publicações 
(MARTIN;NEWKIRK; KOSS, 2003), os Princípios SOLID. Eles compreendem cinco 
técnicas de programação orientada a objetos que facilitam o desenvolvimento 
de software, tornando-o mais compreensível, flexível e de fácil manutenção. 
O acrônimo SOLID é formado pela letra inicial de cada uma das técnicas. Veja 
um resumo no Quadro 1.
Quadro 1. Resumo dos conceitos SOLID
Letra Sigla Nome Definição
S SRP Princípio da Responsa-
bilidade Única (Single 
Responsibility Principle)
Uma classe deve ter uma, 
e somente uma, razão para 
mudar.
O OCP Princípio Aberto-Fechado 
(Open Closed Principle)
Você deve ser capaz de es-
tender um comportamento 
de uma classe sem precisar 
modificá-la.
L LSP Princípio da Substituição 
de Liskov (Liskov Substitu-
tion Principle)
As classes-base devem ser 
substituíveis por suas classes 
derivadas.
(Continua)
Pensamento computacional para sistemas de larga escala 9
Letra Sigla Nome Definição
I ISP Princípio da Segregação da 
Interface (Interface Segre-
gation Principle)
Interfaces específicas são 
melhores do que uma interface 
geral.
D DIP Princípio da inversão da 
dependência (Dependency 
Inversion Principle)
Dependa de abstrações, não de 
implementações.
Fonte: Adaptado de Martin, Newkirk e Koss (2003).
Os princípios SOLID são fortemente ligados ao paradigma de orientação 
a objetos e suas técnicas são voltadas para a escrita de código padronizada, 
de forma que seja mais simples aumentar a escala do sistema ou realizar 
manutenções. Veja, abaixo, uma descrição mais aprofundada sobre os cinco 
princípios SOLID.
 � Princípio da Responsabilidade Única: cada classe (também aplicável a 
métodos) implementada no sistema deve possuir somente uma respon-
sabilidade (MARTIN; NEWKIRK; KOSS, 2003). Considere responsabilidade 
como qualquer ação atribuída para a classe; assim, para estar de acordo 
com o princípio, a classe não deve ter responsabilidades fora do seu 
contexto. Ela deve possuir um único tipo de tarefa. Por exemplo, uma 
classe responsável pelo cadastro de usuários no sistema deve conter 
apenas funcionalidades para cadastro. Caso ela necessite enviar um 
e-mail de confirmação para completar o cadastro, essa função deve 
estar em outra classe, especializada em enviar e-mails. Deve-se separar 
cada funcionalidade em classes, mesmo que se pareça estar sobrecar-
regando o sistema com diversas classes. Por outro lado, cada classe 
será mais simples de compreender e sua manutenção será facilitada.
 � Princípio do Aberto/Fechado: sua formalização afirma que objetos 
ou entidades devem estar abertos (disponíveis) para extensão, mas 
fechados para receber modificações. Ou seja, você deve ser capaz de 
realizar herança de comportamentos de outra classe, mas não deve 
reescrever seu código original (MARTIN; NEWKIRK; KOSS, 2003). Para 
isso, segundo Martin, Newkirk e Koss (2003), você deve separar qualquer 
funcionalidade que possa ser estendida em uma estrutura chamada de 
interface, depois inverter as dependências. Na prática, deve-se optar 
(Continuação)
Pensamento computacional para sistemas de larga escala10
por interfaces e, se elas estiverem bem definidas, os sistemas estarão 
abertos para extensão.
 � Princípio da Substituição de Liskov: segundo Martin, Newkirk e Koss 
(2003), uma classe derivada deve ser substituível por sua classe-base, ou 
seja, todas as classes que herdam um método (classe filha ou derivada) 
de uma classe pai não devem repetir a funcionalidade já implementada 
nessa classe pai (a classe-base). Seguindo esse conceito, a classe pai 
deve poder ser substituída por qualquer uma de suas subclasses em 
qualquer região do código. Esse princípio permite aplicar o polimorfismo 
de forma mais segura. Com ele, podemos utilizar métodos de classes 
filhas implementando a classe pai sem preocupações com resultados 
inesperados. Geralmente utilizamos esse princípio associado a outros, 
como o Aberto/Fechado e a Segregação de Interface.
 � Princípio da Segregação de Interface: uma classe não deve ser com-
pelida a implementar interfaces e funcionalidades que não serão uti-
lizadas. Resumindo, é melhor criar várias interfaces específicas do 
que somente uma interface genérica (MARTIN; NEWKIRK; KOSS, 2003).
 � Princípio de Inversão de Dependência: caso seja necessário criar alguma 
dependência, evite que componentes de alto nível dependam de com-
ponentes de baixo nível. Ou seja, um componente mais especializado 
não deve depender de um componente menos especializado. Caso seja 
necessário, deve-se criar uma classe abstrata com as funcionalidades e 
fazê-las depender da abstração. O Princípio da Inversão de Dependência 
é um princípio essencial para um bom design orientado a objetos, ao 
passo que o oposto leva ao aumento do acoplamento entre os módulos.
Esses conceitos podem ser aplicados a qualquer linguagem de progra-
mação orientada a objetos (Java, por exemplo) e, embora pareça um pouco 
complicado no início, quando aprendidos e implementados corretamente, 
ajudam os desenvolvedores a criar aplicações de larga escala que permitem 
extensões, modificações, testes e refatoração com dificuldade reduzida.
Padrões
Em meados da década de 1970, um engenheiro civil chamado Cristopher 
Alexander percebeu que as construções da época seguiam, da menor a mais 
sofisticada, padrões bem semelhantes. Para cada tipo de estrutura, os proble-
mas eram sempre os mesmos, e as soluções aplicadas eram muito parecidas. 
Então, ele catalogou os problemas observados e descreveu as soluções para 
Pensamento computacional para sistemas de larga escala 11
cada caso. Assim, foi publicada The Timeless Way of Building (ALEXANDER, 
1979), considerada como a primeira bíblia da engenharia civil, que tratava 
exatamente de padrões para construção na área da engenharia civil.
Com o mesmo objetivo, descrever um problema que ocorre repetidamente 
e um conjunto reutilizável de soluções para esse problema, em 1995, os auto-
res Erich Gamma, Richard Helm, Ralph Johnson e John Vlissides publicaram o 
livro Design patterns: elements of reusable object-oriented software (GAMMA 
et al., 1995), traduzido pela Editora Bookman em 2000, catalogando mais de 
20 padrões de solução de problemas e suas aplicações. O livro lhes rendeu o 
apelido de “Gangue dos Quatro” (Gang of Four, ou GoF) e ainda hoje é referência 
para desenvolvimento orientado a objetos.
Um padrão de software caracteriza muitas situações que um progra-
mador provavelmente encontrará e oferece orientação sobre como 
estruturar o programa para melhor se ajustar ao padrão. Mas não confunda 
padrão de projeto com reaproveitamento de código, pois padrões de projeto não 
estão ligados somente à codificação. Em vez de pensar somente em reutilização 
de código, com padrões você tem reutilização de experiência!
Segundo o catálogo do GoF (GAMMA et al., 1995), os padrões são divididos 
em três categorias: de criação, estrutural e comportamental. Mas antes de 
falar das categorias, é importante comentar que os padrões de objeto, além 
das categorias, podem ser classificados também em relação a seu escopo: 
de classe ou de objetos. Padrões com escopo de classe vão utilizar a herança 
para compor ou variar os objetos, mantendo a flexibilidade do sistema. Já 
os padrões de objeto vão delegar suas responsabilidades para um objeto.
 � Criação: os padrões de criação são aqueles que criam objetos para você, 
em vez de instanciar objetos diretamente. Isso dá, a seu programa, 
mais flexibilidade para decidir quais objetos precisam ser criados para 
determinado caso.
 � Estrutural: os padrões estruturais são aqueles relacionados à com-
posição de classes e de objetos. Eles usam herança para compor in-
terfaces e definem maneiras de construir objetos para obter novas 
funcionalidades.
Pensamento computacional para sistemas de larga escala12
 � Comportamental: a maioria desses padrões de design está especifi-
camente relacionada à comunicação entre objetos.
No Quadro 2, são apresentados todos os padrões descritos no livro, cada 
umjá categorizado conforme seu escopo e propósito. Note que a maioria dos 
nomes é intuitiva, facilitando sua identificação e aplicação.
Quadro 2. Classificação dos padrões segundo GoF
Propósito
Criação Estruturais Comportamentais
Es
co
po
Cl
as
se Factory Method Adapter (class) Interpreter
Template Method
O
bj
et
o
Abstract Factory
Builder
Prototype
Singleton
Adapter (object)
Bridge
Composite
Decorator
Façade
Flyweight
Proxy
Chain of Responsibility
Command
Iterator
Mediator
Memento
Observer
State
Strategy
Visitor
Fonte: Adaptado de Gamma et al. (1995).
Agora falando especificamente de cada um dos padrões de projeto (ou 
design patterns), eles descrevem uma solução geral e reutilizável para um 
problema frequente no desenvolvimento de sistemas orientados a objetos. 
Um padrão não se trata de modelos ou classes prontas para uso, mas de 
descrições de como resolver o problema do qual ele trata, que pode ser 
usado (e até adaptado) em muitas situações diferentes. Eles não são ligados 
somente à codificação, mas também a formas de solucionar questões de 
desenvolvimento com base em soluções com eficácia comprovada. Em vez de 
pensar somente em reutilização de código, com padrões você tem reutilização 
de experiência de outros desenvolvedores.
Pensamento computacional para sistemas de larga escala 13
Cada padrão de projeto apresenta os mesmos itens básicos e, estrutural-
mente, segue a mesma disposição:
 � Nome
 � Problema
 ■ Quando aplicar o padrão.
 � Solução
 ■ Descrição que comunica o problema e como usar classes e objetos 
para o resolver.
 � Consequências
 � Custo-benefício de usar o padrão
 ■ Impactos no sistema (flexibilidade, extensibilidade, portabilidade 
e eficiência do sistema).
Em Gamma et al. (1995), cada padrão é extensamente detalhado, 
incluindo situações de uso, exemplos de codificação, cenários, etc. 
Como exemplo, abaixo é apresentado resumidamente o padrão estrutural 
Adapter.
O padrão estrutural Adapter converte a interface de uma classe em outra 
interface que o cliente espera. Assim, permite que classes que normalmente não 
poderiam trabalhar juntas, devido à incompatibilidade de interfaces, possam 
fazê-lo. Em outras palavras, imagine que você necessita ligar um plugue de 
pinos chatos em uma tomada com três furos usando um adaptador de tomada. 
O padrão Adapter utiliza o mesmo conceito, criando uma forma para que as duas 
interfaces possam se comunicar.
Use o Adapter quando:
 � você quer usar uma classe existente, mas sua interface não é adequada 
àquela que você precisa;
 � você quer criar uma classe reusável que coopera com classes não relaciona-
das ou não previstas, isto é, classes que não necessariamente têm interfaces 
compatíveis;
 � você precisa usar várias subclasses existentes, mas é impraticável adaptar 
suas interfaces especializando cada uma. Um object adapter pode adaptar 
a interface de suas classes pai.
Atualmente, diversas linguagens e Frameworks incorporaram alguns desses 
padrões. O Dot Net da Microsoft, por exemplo, tem disponível o componente 
de acesso a dados ADO.net, que utiliza os padrões Adapter e Command. 
Pensamento computacional para sistemas de larga escala14
Outro exemplo de padrão para construção é o padrão GRASP (abreviatura 
de General Responsibility Assignment Software Patterns), livremente traduzido 
como Padrões de Software Atribuídos à Responsabilidade Geral (LARMAN, 
2006), que descreve princípios fundamentais de atribuição de responsabili-
dade a objetos e são recomendações para melhor documentar e padronizar 
princípios antigos e exaustivamente testados de design orientado a objetos. 
Os diferentes patterns e princípios usados em GRASP são detalhados abaixo.
 � Controller (controlador): encarrega a responsabilidade de lidar com 
os eventos do sistema a uma classe de interface gráfica (utilizado no 
MVC [model-view-controller]).
 � Creator (criador): incumbido da criação de objetos a partir de classes 
(similar ao Factory do GoF).
 � Indirection (indireção): reduz o acoplamento entre componentes de 
software atribuindo a mediação da relação entre os dois a uma terceira 
classe (usado no MVC).
 � Information Expert (especialista): utilizado para distribuir as respon-
sabilidades entre as classes, sejam métodos, atributos, etc.
 � High Cohesion (alta coesão): padrão que tenta conservar os objetos 
gerenciáveis, focados e compreensíveis.
 � Low Coupling (baixo acoplamento): para diminuir a dependência entre 
as classes, diminuir o impacto que as alterações em uma causam nas 
outras e aumentar o potencial de reúso das classes.
 � Polymorphism (polimorfismo): a responsabilidade de estabelecer 
variações de comportamentos baseada no tipo é imputada aos tipos 
para os quais essa variação é verificada.
 � Protected Variations (variáveis protegidas): resguarda um componente 
das variações ocorridas em outros componentes. Para isso, o foco da 
instabilidade é encapsulado por uma interface, utilizando polimorfismo 
para criar as implementações dessa interface.
 � Pure Fabrication (fabricação própria): classes artificiais especialmente 
criadas para alcançar baixo acoplamento, alta coesão e potencial reuso. 
Não representam qualquer conceito do domínio do problema.
Além do GoF e do GRASP, outros tantos padrões podem ser empregados, 
como padrões J2EE da Sun, os padrões JSP, padrões arquiteturais, padrões 
de projetos de jogos, etc.
Pensamento computacional para sistemas de larga escala 15
Dificuldades no desenvolvimento de 
aplicações reais
A produção de um software guarda muitas diferenças em comparação com 
as produções de outras engenharias, sobretudo se compararmos o avanço 
do hardware ao do software. Brooks (1986), em ensaio denominado “No Silver 
Bullet” (traduzindo, “Sem bala de prata”), descreveu suas observações e 
teceu uma análise sobre as particularidades da área baseado no contexto da 
época. Ele dividiu os problemas na produção de software em duas categorias: 
acidentais e essenciais. Os problemas acidentais estão ligados principalmente 
a limitações tecnológicas, enquanto os problemas essenciais estão ligados 
à natureza do software, de modo que improvavelmente algum dia poderão 
ser superados por qualquer inovação tecnológica ou metodologia criada.
Os problemas acidentais, como estão ligados a dificuldades tecnológicas, 
são mais simples de resolver caso o profissional esteja devidamente capa-
citado e tenha acesso aos devidos recursos e tecnologias. As dificuldades 
acidentais foram reduzidas graças ao aprimoramento de tecnologias, como 
linguagens de alto nível, e avanços em hardware e em sistemas operacionais 
(DENNING; TEDRE, 2019).
As dificuldades essenciais, segundo Brooks (1986), são naturalmente ge-
radas pela característica abstrata do software. Tal particularidade o torna 
intangível e complexo de estimar, dificultando qualquer estimativa de esca-
labilidade ou esforço para construção. Outro problema essencial se deve a 
suas naturais complexidade e irredutibilidade, o que torna impossível de ser 
simplificado sem que ocorra perda significativa de informação (BROOKS, 1986).
No mesmo artigo, Brooks (1986) apresenta quatro características que 
afetam o processo de desenvolvimento de software e tornam sua construção 
essencialmente complexa. Vejamos.
1. Complexidade: muitos dos problemas do software são derivados de sua 
complexidade quanto ao crescimento não linear. Ampliar a escala de 
um sistema não consiste em alterar o tamanho de suas partes, como 
é feito com qualquer outra construção física, como componentes de 
hardware, cuja escala pode ser variada aumentando ou reduzindo o 
tamanho de seus componentes.
2. Conformidade: software precisa se adaptar ao contexto, que pode 
mudar a qualquer momento. Por exemplo, caso uma legislação traba-
lhista seja alterada, espera-se que sistemas relacionados a esse tipo 
de legislação se adaptem rapidamente.
Pensamento computacional para sistemas de larga escala16
3. Mutabilidade: quando um produto físico fica obsoleto, porexemplo, 
geralmente é substituído por um modelo atualizado, considerando 
que os custos e a complexidade para reconstrução do produto não 
compensariam o esforço. Devido a sua natureza intangível, o software 
está sempre sofrendo mudanças. Outrossim, boa parte das vezes, são 
solicitadas mudanças que ultrapassam seus limites originais.
4. Invisibilidade: por ser um bem imaterial e de natureza abstrata, um 
software não pode ser demonstrado visualmente. Por mais conheci-
mento que possuam, nem usuário, nem programador conseguem ter 
uma visão completa do software, pois geralmente um lado não com-
preende todas as questões tecnológicas e o outro desconhece todas 
as regras de negócio envolvidas, ainda mais se o desenvolvimento for 
em equipe, quando o conhecimento é mais distribuído ainda. A falta 
de visão do todo acarreta o aumento da probabilidade de que erros 
na construção ocorram.
Essas dificuldades são inerentes ao software, de forma que algumas delas 
podem nunca ocorrer em outras áreas da engenharia. Utilizemos como exemplo 
a construção de um objeto doméstico relativamente comum, uma geladeira, 
para comparar com as dificuldades essenciais definidas por Brooks (1986).
 � Caso o fabricante queira produzir geladeiras com tamanhos diferentes, 
é possível mudar a escala das peças e produzir um equipamento maior, 
o que, como vimos, não é viável do caso de software.
 � A construção de uma geladeira segue normas e legislações específicas; 
porém, quando elas são alteradas, os fabricantes têm anos para se 
adaptar (ou se conformar) às novas leis, diferentemente do que ocorre 
com software.
 � As geladeiras dificilmente ganham novas funcionalidades, sobretudo 
depois que foram vendidas. Até onde se tem conhecimento, nenhum 
fabricante resolve adicionar portas depois que o produto está na linha 
de montagem ou mesmo em um produto que já está na posse do cliente 
final. Com software, porém, essa mutabilidade é possível.
 � Finalmente, a geladeira é um objeto com peso, altura, volume interno, 
etc., que gera base para precificação e comparação pelos consumidores 
finais, o que não acontece com software.
Pensamento computacional para sistemas de larga escala 17
Perceba que as características particulares de cada engenharia podem 
não ser afetadas pelas dificuldades essenciais; ao mesmo tempo, elas podem 
ter impactos consideráveis no desenvolvimento do software e estão ligadas, 
principalmente, à capacidade do ser humano de compreender a essência de 
problemas complexos.
Essas dificuldades essenciais são tão significativas que receberam 
uma analogia interessante, que inclusive dá o título ao artigo mencionado. 
A menção a “bala de prata” é uma analogia às tentativas de encontrar uma 
solução para o problema do software. O autor faz uma comparação entre 
a lenda do licantropo (lobisomem da cultura popular) com o problema da 
complexidade do software. Em relação ao ser sobrenatural, basta uma única 
bala de prata para que seja possível salvar o dia, ao contrário dos problemas 
que envolvem a produção de software, pois, considerando as dificuldades 
essenciais, inexiste uma solução única, a “bala de prata”.
Atualmente, essas dificuldades enfrentadas pela engenharia de software 
estão cada vez mais amplificadas com o advento de novas tecnologias e 
necessidades. Denning e Tedre (2019) elencam alguns desses novos desafios. 
Vejamos.
 � Intrusões e malwares: quanto mais escalares os sistemas, mais com-
plexo é garantir a ausência de vulnerabilidades. Criminosos virtuais 
estão sempre buscando brechas que possam ser exploradas; Tais aces-
sos indevidos podem não só comprometer severamente a privacidade 
do proprietário, como também podem danificar a máquina infectada;
 � Tolerância a falhas: a complexidade inerente ao software e sua de-
pendência do hardware causa impactos na garantia de que o sistema 
se recupere adequadamente mesmo após a ocorrência de falhas em 
alguns componentes. Caso isso ocorra, a qualidade do serviço é reduzida 
proporcionalmente à severidade da falha.
 � Hardware seguro: tentativas de explorar vulnerabilidade também 
ocorrem em nível de hardware, direcionadas às camadas mais baixas 
do núcleo e à rede, explorando a incapacidade de manutenção de 
monitoramento eficiente. Atualmente, com a intensificação do uso 
de tecnologias baseadas em IoT (Internet of Things, ou Internet das 
Coisas), preocupações com a segurança em nível de hardware voltaram 
à discussão.
 � Algoritmos de machine learning: uma preocupação recorrente com 
machine learning (aprendizado de máquina, em tradução para o por-
tuguês) são as falhas decorrentes de erros em seu treinamento. Como 
Pensamento computacional para sistemas de larga escala18
saber se as situações que foram descartadas do treinamento não são 
justamente os pontos de possíveis falhas? A complexidade em tentar 
responder aumenta conforme novas camadas de neurônios são adi-
cionadas a uma intrincada sequência de conexões.
 � Segurança: sistemas críticos estão inseridos em diversos ambientes: 
monitores cardíacos, controladores de temperatura em usinas ter-
monucleares, equipamentos de voo em uma aeronave comercial, etc. 
Falhas em qualquer desses cenários podem ser catastróficas, tanto 
em âmbito patrimonial quanto para a vida.
 � Produção em massa de diversos produtos de software: com a crescente 
procura por aplicativos em geral, sua produção também deve ser am-
pliada e acelerada, muitas vezes incluindo módulos ou funcionalidades 
de terceiros para agilizar a conclusão e atender à demanda. Nem sempre 
o desenvolvedor avalia a implementação das dependências de sua 
aplicação, levando complexidade ou mesmo riscos de segurança para 
sua construção.
Perceba que as características particulares de cada engenharia podem 
não ser afetadas pelas dificuldades essenciais. Ao mesmo tempo, elas po-
dem impactar consideravelmente o desenvolvimento do software e estão 
ligadas, sobretudo, à capacidade do ser humano de compreender a essência 
de problemas complexos.
Transcorridos mais de 50 anos da histórica Conferência da OTAN, é notável 
a quantidade de avanços desenvolvidos, de novas metodologias e técnicas 
para a construção de software. O pensamento computacional precisa ser 
desafiado constantemente a continuar se desenvolvendo, auxiliando, desse 
modo, na criação de novos recursos conforme os avanços tecnológicos con-
tinuam apresentando novos desafios.
Referências
ALEXANDER, C. The timeless way of building. Oxford: Oxford University Press, 1979.
ARREGUY-SENA, C. Proposta de fluxo de dados no projeto de informatização do hospital-
-dia para infectados pelo HIV em Juiz de Fora – MG. Revista Mineira de Enfermagem, 
v. 3, nº 1, p. 46–53, 1999.
BROOKS JR., F. P. No silver bullet: essence and accidents of software engineering. 
IEEE Computer, v. 20, nº 4, p. 10–19, 1986. Disponível em: http://worrydream.com/refs/
Brooks-NoSilverBullet.pdf. Acesso em: 29 dez. 2020.
DENNING, P. J.; TEDRE, M. Computational thinking. Cambridge: MIT Press, 2019.
Pensamento computacional para sistemas de larga escala 19
GAMMA, E. et al. Design patterns: elements of reusable object-oriented software. 
Boston: Addison-Wesley, 1995.
LARMAN, C. Utilizando UML e padrões: uma introdução à análise e ao projeto orientados 
a objetos e ao desenvolvimento iterativo. 3. ed. Porto Alegre: Bookman, 2006.
MARTIN, R. C.; NEWKIRK, J. W.; KOSS, R. S. Agile software development: principles, 
patterns, and practices. Upper Saddle River: Pearson, 2002.
RILEY, D.; HUNT, K. A. Computational thinking for the modern problem solver. Boca 
Raton: CRC Press, 2014.
SALTZER, J. H.; SCHROEDER, M. D. The protection of information in computer systems. 
Proceedings of IEEE, v. 63, nº 9, p. 1278–1308, 1975. Disponível em: http://web.mit.edu/
Saltzer/www/publications/protection/. Acesso em: 29 dez. 2020.
SOMMERVILLE, I. Engenharia de software. 8. ed. São Paulo: Person, 2007.
VALENTE, M. T. Engenharia de software moderna: princípios e práticas para desenvol-
vimento de softwarecom produtividade. Belo Horizonte: Marco Tulio Valente, 2020.
WIRTH, N. A brief history of software engineering. IEEE Annals of the History of Com-
puting, v. 30, nº 3, p. 32–39, 2008.
Leituras recomendadas
BEECHER, K. Computational thinking: a beginner's guide to problem-solving and pro-
gramming. Swindon: BCS, 2017.
GAMMA, E. et al. Padrões de projeto: soluções reutilizáveis de software orientado a 
objetos. Porto Alegre: Bookman, 2000.
Os links para sites da web fornecidos neste capítulo foram todos 
testados, e seu funcionamento foi comprovado no momento da 
publicação do material. No entanto, a rede é extremamente dinâmica; suas 
páginas estão constantemente mudando de local e conteúdo. Assim, os edito-
res declaram não ter qualquer responsabilidade sobre qualidade, precisão ou 
integralidade das informações referidas em tais links.
Pensamento computacional para sistemas de larga escala20
Dica do professor
Ao iniciar um projeto, o desejo de construir o melhor código possível, de prever necessidades antes 
mesmo que elas ocorram ou de reduzir o tempo de entrega do projeto pode vir a criar grandes 
desafios, podendo causar impactos negativos no momento de expandir a escala do software ou de 
realizar manutenções necessárias.
Para nortear o desenvolvimento, provendo melhor reaproveitamento de experiências entre a 
equipe e facilitando alterações futuras, o desenvolvedor poderá ter em mente alguns dos princípios 
de projeto de software.
Determinados princípios da engenharia de software podem não ter grande efeito em sistemas 
pequenos, com poucas funcionalidades, visto que algumas dessas técnicas incluiriam complexidade 
desnecessária ao projeto. Todavia, para sistemas em grande escala, essa complexidade de escrita é 
compensada pelo tempo economizado no reúso de componentes e na comunicação entre os 
membros da equipe.
Nesta Dica do Professor, conheça os conceitos básicos de padrões de projeto e qual sua finalidade 
em um projeto de software.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
 
Exercícios
1) A engenharia de software foi instituída em meados da década de 1960 devido a diversos 
casos de falhas catastróficas ocasionadas por softwares mal construídos. Ela direciona 
esforços a diversas áreas do Pensamento Computacional, como as linguagens de 
programação, padrões, bancos de dados, processos e qualidade de software, dentre outras. 
Considerando os conceitos e as motivações para a instituição da engenharia de software, 
assinale a alternativa correta:
A) Usar o termo engenharia foi sugerido para aproveitar a fama das engenharias para reduzir a 
descrença causada pelas falhas dos sistemas.
B) A engenharia de software surgiu pela urgente necessidade de correção das falhas ocorridas no 
software das sondas espaciais.
C) A engenharia de software surgiu da necessidade de utilização de princípios de engenharia para 
a especificação, o desenvolvimento e a manutenção de sistemas de software.
D) Tem como principal objetivo a construção de modelos teóricos e fundamentações 
matemáticas baseados na engenharia clássica. 
E) Nas últimas décadas, fez a especificação de padrões baseados na engenharia para evitar 
práticas antigas como reutilização de código. 
Dentre as contribuições da engenharia de software para a área de desenvolvimento, estão a 
definição de princípios para construção de projetos. Existem várias definições e autores que 
tratam do tema. Uma das definições conhecidas são os Sete Princípios de Presmann.
Analise as afirmativas a seguir e classifique-as em verdadeiras (V) ou falsas (F):
( ) As decisões tomadas durante a construção do software devem buscar uma meta: agregar 
valor aos seus usuários. 
( ) Os projetos devem se manter tão simples quanto possível e tal tarefa exige muito 
esforço. 
( ) Ao construir um sistema de software, deve-se implementar pensando que mais alguém 
terá que compreender o que foi feito. 
( ) Reúso sempre poupa tempo e esforço; assim, conseguir um alto nível de reúso é a 
principal meta a ser alcançada. 
2) 
( ) Raciocinar clara e completamente antes da ação aumenta a probabilidade de 
funcionar adequadamente.
Assinale a alternativa que preenche as lacunas de forma correta:
A) V, V, F, V, F.
B) F, F, V, F, V.
C) V, V, V, F, V.
D) V, F, V, F, V.
E) V, F, F, V, F.
3) A etapa de Projeto de Software é uma metodologia da engenharia de software que se 
preocupa com todo o planejamento anterior ao desenvolvimento.
Analise as afirmativas a seguir e classifique-as em verdadeiras (V) ou falsas (F):
( ) Considerando os conceitos de construção de software utilizando orientação a objetos, 
cada componente de software é constituído por uma única classe. 
( ) Conforme o Liskov Substitution Principle, caso o componente troque a classe base pela 
superclasse respectiva, seu funcionamento deve se manter o mesmo. 
( ) Quando um componente não depende de classes concretas, e, sim, de abstrações (por 
exemplo, uma interface), é possível dizer que está seguindo o princípio da inversão de 
dependência.
Assinale a alternativa que preenche as lacunas de forma correta:
A) F, F, V.
B) V, F, F.
C) F, V, F.
D) V, V, F.
E) F, V, V.
O produto construído por meio da engenharia de software tem particularidades distintas de 
qualquer constructo implementado pelas demais engenharias, em destaque quando são 
comparados software e hardware. Em seu clássico trabalho denominado "Não Existe Bala de 
4) 
Prata", Frederick Brooks discorreu e elencou problemas inerentes à área da engenharia de 
software.
Considerando os problemas discutidos e a construção de aplicações em larga escala, assinale 
a alternativa correta:
A) O fato de o software não ter forma física é vantagem para o desenvolvedor que pode, de 
maneira mais simplificada, defender estimativas de esforço junto a seu cliente.
B) As dificuldades identificadas por Brooks podem ser classificadas como essenciais e acidentais, 
mas somente as essenciais são capazes de causar problemas em aplicações reais. 
C) O impacto de uma adaptação por necessidade de conformidade de uma interface em um 
sistema é inversamente proporcional ao impacto causado pelo aumento de complexidade de 
uma aplicação. 
D) A engenharia de software tem fundamentos básicos inerentes às demais engenharias, sendo 
que a expressão bala de prata é sempre utilizada em alusão à indústria bélica.
E) Os produtos de software estão entre os mais complexos gerados por engenharia e tem 
dificuldades essenciais intrínsecas, como a complexidade, a invisibilidade e a mutabilidade.
A engenharia de software é uma das áreas de estudo que evoluiu consideravelmente os 
processos voltados à criação de softwares, pois traz conceitos, princípios e padronizações 
que até hoje são utilizados, servindo de base para a construção de sistemas de alta 
complexidade.
Analise as afirmativas a seguir, que tratam de conceitos gerais sobre engenharia de software, 
e classifique-as em verdadeiras (V) ou falsas (F):
( ) Um dos problemas do software é que seus processos evoluem muito mais rápido do que 
aqueles relacionados ao hardware.
( ) Qualquer projeto de software deve ter como meta atender às necessidades de algum 
negócio.
( ) A engenharia de software não busca desenvolvimento de teorias e fundamentações. Seu 
objeto de estudo são as práticas de desenvolvimento de software.
( ) Diversos princípios foram definidos pela engenharia de software, tais como a abstração, 
que filtra os elementos importantes sem ignorar nenhum detalhe.
( ) A engenharia de software não pode ser confundida com a Ciência da Computação, pois, 
enquanto uma busca teorias e fundamentações para temas computacionais, a outra tem 
5) 
foco na construção de software.
Assinale a alternativa que preenche as lacunas de forma correta:
A) V, V, F, V, V.
B) F, F, V, F, V.
C) V, F, F, V, F.
D) F, V, V, F, V.
E) V, F, V, V, F.
Na prática
Algumas empresas de software, logo que iniciam sua atuação, em benefícioda rápida entrega e do 
aumento do número de clientes, optam por não empregar determinadas técnicas da engenharia de 
software, justamente pela complexidade inicial que algumas delas trazem intrinsecamente.
Ao longo do tempo, conforme aumentam a escala dos projetos, o tamanho da equipe e a 
quantidade de manutenções, fica clara a necessidade de padronizar determinadas atividades em 
prol de viabilizar o aumento dos projetos e a comunicação entre os membros da equipe. Para tanto, 
os padrões e os princípios da engenharia de software podem servir de guia para a organização e a 
implantação de melhorias nos projetos.
Acompanhe, neste Na Prática, a utilização de conceitos da engenharia de software para a 
construção de sistemas em equipes de desenvolvimento.
Aponte a câmera para o 
código e acesse o link do 
conteúdo ou clique no 
código para acessar.
Saiba +
Para ampliar o seu conhecimento a respeito desse assunto, veja abaixo as sugestões do professor:
Conheça os padrões de projeto
Neste artigo, são apresentados os padrões de projeto, que propiciam projetar soluções de software 
com melhor qualidade e menor custo.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
Princípios da engenharia de software
Veja, neste artigo, uma introdução à engenharia de software e os sete princípios para a produção de 
software, segundo o pesquisador David Hooker.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
Padrões de projeto
Neste vídeo, conheça um pouco mais sobre os conceitos básicos de padrões de projetos (Design 
Patterns).
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
SOLID Principles: melhorando o design do seu código
Neste artigo, conheça um pouco melhor este conjunto de orientações para a escrita de código que 
favorece legibilidade, manutenção e evolução do sistema.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
O que é pensamento computacional e para que ele serve?
Neste vídeo, conheça um pouco mais sobre Pensamento Computacional.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.
A conceptual framework for a software development process 
based on Computational Thinking
Neste artigo, em inglês, acompanhe a apresentação de uma proposta de sistemática para o 
desenvolvimento de software usando as possibilidades do Pensamento Computacional.
Aponte a câmera para o código e acesse o link do conteúdo ou clique no código para acessar.

Mais conteúdos dessa disciplina