Ir ao conteúdo

Posts recomendados

Postado

Tento executar um exemplo de código do livro, na páginas 121 e 122, e não mostra as palavras digitadas, tal como refere o autor. Segue o programa abaixo. Incluí um comando break no while para não ter de interromper com ctrl+z. Deveria classificá-las e mostrar na tela.

#include <iostream>
#include <vector>
#include <algorithm>
#include <string>
using namespace std;

int main()
{
	vector<string>palavras;
	string temp;
	while (cin>>temp)
    {
		if (temp == "sair")
			break;
		else
			palavras.push_back(temp);
	}
	cout << "Numero de palavras: " << palavras.size() << endl;
	sort(palavras.begin(), palavras.end());
	for (unsigned int i; i<palavras.size(); ++i)
		if (i==0 ||palavras[i-1]!=palavras[i])
			cout << palavras[i] << "\n";
return 0;
}

image.png.ee8ed777682af899008c2040f6eb19f0.png

Postado

@MUrisCuri    no loop for para mostrar as palavras , você colocou insigned int i , mas não inicializou essa variáveL  i  ,  que pode ter qualquer valor  e ninguém sabe qual é , e ai qual palavra vai escrever se não tem o índice dela no vetor .

Postado
1 hora atrás, MUrisCuri disse:

um exemplo de código do livro, na páginas 121 e 122, e não mostra as palavras digitadas, tal como refere o autor

 

Isto foi de fato publicado? Não faz sentido. É um programa muito ruim para estar em um livro, falando objetivamente.

 

se palavras é  vetor<string> o simples em C++ é usar um iterator.

 

Não usou. 

 

Mas usou no sort então sabe que existe um iterator

 

Se usou no sort porque usar um for logo a seguir e não usar um iterador se já sabe o que é?

 

Se usa <vector> e <algorithm> não devia estar usando esse tipo de loop dos anos 80...

 

como @devair1010 explicou você deve inicializar a variável de controle do loop. Aquele loop  que não deveria estar usando. E se não estivesse usando não teria errado. ;) 

 

 

 

 

 

 

 

 

Postado

@JorgeGus  continua errado. Se o sistema iniciar aquela área de alguma forma com zero vai funcionar, até o dia em que não funcionar :) 
 

  • de modo geral, inicialize todas variáveis
     
  • não precisa usar unsigned int, basta unsigned
     
  • não precisa usar unsigned. Basta auto, desde 2011
     
  • não deve usar esse tipo de instrução, basta um range for, desde 2011
     
sort(palavras.begin(), palavras.end());

for (unsigned int i=0; i<palavras.size(); ++i)
    if (i==0 ||palavras[i-1]!=palavras[i])
        cout << palavras[i] << "\n";


Não conheço esse livro, mas fico curioso pelo que o autor tenta fazer com esse loop.


Aparentemente apenas queria mostrar só as linhas não repetidas do vetor e assim usou 'i == 0' na primeira condição porque a linha zero não tem antecessora e no segundo teste (i-1) ficaria negativo para a primeira string

 

Mas se está usando STL e <algorithm> para que 😈 usar sort e um vector e não usar um set já que por definição em um conjunto os elementos ficam em ordem e sem duplicidade????

 

Veja a saída 

 

Tecle Control-Z para encerrar a leitura

D
C
BBB
AAA
2
^Z
2
AAA
BBB
C
D

 

Deste programa

 

#include <fstream>
#include <iostream>
#include <iterator>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    set<string> palavras{ in,FIM };
    for (auto palavra : palavras) cout << palavra << "\n";
    return 0;
}

 

E considere esse mais moderno que daria na mesma
 

#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    ostream_iterator<string> saida{ cout,"\n" };
    set<string> palavras{ in,FIM };
    copy(palavras.begin(), palavras.end(), saida);
    return 0;
}

 

Ou esse mais moderno ainda (C++20) usando ranges
 

#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <ranges>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    ostream_iterator<string> saida{ cout,"\n" };
    set<string> palavras{ in,FIM };
    ranges::copy( palavras, saida);
    return 0;
}

 

  • Curtir 1
Postado
38 minutos atrás, arfneto disse:

@JorgeGus  continua errado. Se o sistema iniciar aquela área de alguma forma com zero vai funcionar, até o dia em que não funcionar :) 
 

  • de modo geral, inicialize todas variáveis
     
  • não precisa usar unsigned int, basta unsigned
     
  • não precisa usar unsigned. Basta auto, desde 2011
     
  • não deve usar esse tipo de instrução, basta um range for, desde 2011
     

sort(palavras.begin(), palavras.end());

for (unsigned int i=0; i<palavras.size(); ++i)
    if (i==0 ||palavras[i-1]!=palavras[i])
        cout << palavras[i] << "\n";


Não conheço esse livro, mas fico curioso pelo que o autor tenta fazer com esse loop.


Aparentemente apenas queria mostrar só as linhas não repetidas do vetor e assim usou 'i == 0' na primeira condição porque a linha zero não tem antecessora e no segundo teste (i-1) ficaria negativo para a primeira string

 

Mas se está usando STL e <algorithm> para que 😈 usar sort e um vector e não usar um set já que por definição em um conjunto os elementos ficam em ordem e sem duplicidade????

 

Veja a saída 

 


Tecle Control-Z para encerrar a leitura

D
C
BBB
AAA
2
^Z
2
AAA
BBB
C
D

 

Deste programa

 


#include <fstream>
#include <iostream>
#include <iterator>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    set<string> palavras{ in,FIM };
    for (auto palavra : palavras) cout << palavra << "\n";
    return 0;
}

 

E considere esse mais moderno que daria na mesma
 


#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    ostream_iterator<string> saida{ cout,"\n" };
    set<string> palavras{ in,FIM };
    copy(palavras.begin(), palavras.end(), saida);
    return 0;
}

 

Ou esse mais moderno ainda (C++20) usando ranges
 


#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <ranges>
#include <set>
using namespace std;

int main()
{
    cout << "Tecle Control-Z para encerrar a leitura\n\n";
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    ostream_iterator<string> saida{ cout,"\n" };
    set<string> palavras{ in,FIM };
    ranges::copy( palavras, saida);
    return 0;
}

 

Eu sei que devemos inicializar as variáveis para evitar erros intermitentes com o lixo da memória, acontece que eu rodei o programa dele sem olhar o código para ver se havia alguma mensagem de erro, e por acaso funcionou.

 

E quanto ao livro que ele está usando, me parece que se trata de uma tradução do livro "Programming: Principles and Practice Using C++" publicado em 2008 e o autor é o Bjarne Stroustrup.

Postado

Essa é a tradução da primeira versão do livro que cobre o C++98, a mais atual (2 edição) já é revisada para as versões C++ 11 e C++14. Não achei nenhuma informação de uma terceira edição revisada pra versões mais modernas do C++.

 

Postado
6 minutos atrás, Benjamin Breeg disse:

Essa é a tradução da primeira versão do livro que cobre o C++98, a mais atual (2 edição) já é revisada para as versões C++ 11 e C++14. Não achei nenhuma informação de uma terceira edição revisada pra versões mais modernas do C++.

 

A 2ª edição me parece ter sido a última desse livro mesmo. O livro "A Tour of C++ - 2nd edition" é do mesmo autor e foi publicado em 2018, não sei se é um bom livro, e pra ser sincero apesar do autor ser tão famoso na área, nunca li nenhum livro dele nem do Dennis Ritchie.

Postado
10 horas atrás, MUrisCuri disse:

Na 2ª edição também aparece esse programa, na pág. 182

 

Sim, aparece :) E tem o que faltou no programa que postou. E não tem as mudanças, claro ;)  :) 

 

16 horas atrás, JorgeGus disse:

A 2ª edição me parece ter sido a última desse livro mesmo. O livro "A Tour of C++ - 2nd edition" é do mesmo autor e foi publicado em 2018, não sei se é um bom livro, e pra ser sincero apesar do autor ser tão famoso na área, nunca li nenhum livro dele nem do Dennis Ritchie

Como autores, Dennis Ritchie e Bjarne Stroustrup tem uma posição única nesse caso. Além de autores de livros e publicações Dennis Ritchie (falecido) é o autor de C, a linguagem. E o prof. Bjarne é o autor de C++, a linguagem. E o prof Stroustrup é o criador e um dos mantenedores do C++ core guidelines junto com Herb Sutter. Core guidelines é provavelmente a maior referência em termos de boas práticas de C++. C não tem equivalente, ou teria talvez até 2005 :) mas já vai aí um certo tempo.

 

De volta ao programa
 

Acho que sabe agora o que faltou no seu programa e era simplesmente inicializar i.

 

Explicando porque eu escrevi isso:
 

19 horas atrás, arfneto disse:

Isto foi de fato publicado? Não faz sentido. É um programa muito ruim para estar em um livro, falando objetivamente

 

não poderia de fato associar a algum autor muito menos ao prof. Stroustrup. O problema está nas mudanças que fez. Vou explicar a seguir. (Não me leve a mal, não quis ser rude. Me desculpe por isso).
 

    while (cin>>temp)
    {
        if (temp == "sair")
            break;
        else
            palavras.push_back(temp);
    }

 

 

De todo modo Control-Z (Windows) ou Control-D (Linux) vai "interromper" o loop. trata-se do comportamento de ">>" nesse caso.  Seu programa ainda funciona sem a palavra "sair" porque ">>" para streams ">>" vai retornar nullptr para o fim de arquivo na entrada. lembrando que cin é ifstream.
 

21 horas atrás, MUrisCuri disse:

Segue o programa abaixo. Incluí um comando break no while para não ter de interromper com ctrl+z

 

Você não  "tem que interromper": Control-Z (ou control-D no Unix) vai sinalizar fim de arquivo e ">>" vai retornar nullptr e definir 

eofbit como true. Sempre vai "interromper". Você só criou uma nova condição de parada e excluiu uma possível palavra ;) 

O exemplo original era mais sutil

 

	for(string temp; cin>>temp;) palavras.push_back(temp);

 

porque o prof. Stroustrup sempre escreve assim: em C++ ou C zero é sempre falso. E o for tem uma expressão de saída. Então se pode omitir o incremento, a terceira parte do for, e usar o retorno de >> para encerrar o loop.

 

Note que 
 

	for(string temp; cin>>temp; palavras.push_back(temp) );

 

também funcionaria ok, com o for com as 3 partes e o loop vazio, indicado pelo solitário ';'. Seria menos legível no entanto e acho que por isso o autor preferiu como escreveu.

 

Sua alteração é interessante: o próprio autor do livro prefere while, como você alterou, em relação a um for nessas situações, como ele escreve aqui.
 

Eis o que se procura fazer em Unix

 

EXEMPLO em Linux

 

ch$  echo "\
d
c
b
a
" | ./exemplo
Numero de palavras: 4
a
b
c
d
ch$  

 

Acho que deu para entender. exemplo.c seria esse programa:
 

#include <iostream>
#include <vector>
#include <algorithm>
#include <string>
using namespace std;

int main()
{
	vector<string>palavras;
	for(string temp; cin>>temp;palavras.push_back(temp) );
	cout << "Numero de palavras: " << palavras.size() << "\n";
	sort(palavras.begin(),palavras.end());
	for (unsigned i=0; i<palavras.size(); ++i)
		if ( i==0 || palavras[i-1] != palavras[i])
			cout << palavras[i] << "\n";
	return 0;
}

 

E assim funciona para qualquer entrada, mesmo que tenha "sair".

 

A ideia é sempre nesses casos escrever programas que se possa compor, como num pipe... 

 

no mesmo programa, usando linux e  echo sort e uniq

 

ch$echo "\
forum
forum
clube
clube
do
do
hardware
hardware
hardware" | sort | uniq

 

que mostra no Linux exatamente o que esse program C++ faz:
 

clube
do
forum
hardware  

 

Pega uma lista de strings na entrada, classifica e elimina as duplicatas, mostra na tela as palavras.

 

Mais alinhado com C++ e o que o prof. Stroustrup escreveria hoje seria esse exemplo, como o que mostrei:
 

#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
#include <set>
using namespace std;

int main()
{
    istream_iterator<string> in{ cin };
    istream_iterator<string> FIM{};
    ostream_iterator<string> saida{ cout,"\n" };
    set<string> palavras{ in,FIM };
    copy(palavras.begin(), palavras.end(), saida);
    return 0;
}

 

Note que

  • o autor em questão, o criador da linguagem, é contra o uso de loops comuns, que ele chama de raw for loops
  • incentiva sempre o uso de algoritmos, como copy. E como os algortimos são todos baseados em iterators vai preferir usa-los
  • e como ranges leva a programas mais legíveis ele provavelmente iria escrever hoje sem os iteradores usando ranges, como num outro exemplo que eu mostrei. 
  • incentiva o uso de containers mais especializados --- caso de set --- como ele mesmo usa em A Tour of C++ revisitando esse mesmo problema.
  • Curtir 1
  • 4 semanas depois...
Postado

Arfneto, estou tendo dificuldades na interpretação do enunciado do exercício nº 7, que é seguimento dos anteriores. A dúvida é no início do enunciado:  "Adicione uma unidade a cada double lido; isto é, forneça valores tais como 10cm, 2.5p, 5ft ou 3.33m. Aceite as quatro unidades: cm, m, pol, ft..." A entrada de dados será numérica ou deverá ser número+unidade?

 

Seguem os exercícios em anexo.

 

Meu código até o exercício nº 6 é o seguinte:

 

#include <iostream>
using namespace std;
int main()
{
	double aux_n;
	double temp;
	double v_small;
	double v_larger;
	bool compar=0;
	int i=0;
	cout << "Write 2 numbers: \n";
	++i;
	while ( cin >> temp )
	{
		if (i%2!=0)
		{
			aux_n=temp;
		}
		else
		{
			if (aux_n<temp)
			{
				if (compar==0)
				{
					v_small=aux_n;
					compar=1;
					cout << "The smaller value is " << aux_n << "!" << endl;
					cout << "The smaller value at moment is " << v_small << "!" << endl;
					if (temp-aux_n<1.0/100)
					{
						cout << "The numbers " << temp << " and " << aux_n << " are almost equal." << endl;
					}
				}
				else
				{
					if (aux_n<v_small)
					{
						v_small=aux_n;
						cout << "The smaller value is " << aux_n << "!" << endl;
						cout << "The smaller value at moment is " << v_small << "!" << endl;
					}
					else
					{
						cout << "The smaller value is " << aux_n << "!" << endl;
						cout << "The smaller value at moment is " << v_small << "!" << endl;
					}
				}
			}
			else
			{
				if (aux_n>temp)
				{
					if (compar==0)
					{
						v_larger=aux_n;
						v_small=temp;
						compar=1;
						cout << "The larger value is " << aux_n << "!" << endl;
						cout << "The larger value at moment is " << v_larger << "!" << endl;
						if (aux_n-temp<1.0/100)
						{
							cout << "The numbers " << aux_n << " and " << temp << " are almost equal." << endl;
						}
					}
					else
					{
						if (aux_n>v_larger)
						{
							v_larger=aux_n;
							cout << "The larger value is " << aux_n << "!" << endl;
							cout << "The larger value at moment is " << v_larger << "!" << endl;
						}
						else
						{
							cout << "The larger value is " << aux_n << "!" << endl;
							cout << "The larger value at moment is " << v_larger << "!" << endl;
						}
					}
				}
				else
				{
					cout << "The numbers are the same!" << endl;
				}
			}
		}
	++i;
	}
return 0;
}

 

image.png

Crie uma conta ou entre para comentar

Você precisa ser um usuário para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar agora

Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas comunidades sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×
×
  • Criar novo...

GRÁTIS: ebook Redes Wi-Fi – 2ª Edição

EBOOK GRÁTIS!

CLIQUE AQUI E BAIXE AGORA MESMO!