Sorting with overloaded operators on a pointer array - c++

So, to summarize, I have an array of pointers pointing to objects of class "bookType" whose operators have been overloaded and I am trying to use the selection Sort to sort them by quantity in descending order (ie 10 to 1), yet the order is seemingly random after running this code.
Selection Sort
void selectionSort(bookType *arr[BOOKS], int n){
bookType *temp;
int i, j, minIndex;
for (i = 0; i < n - 1; i++) {
minIndex = i;
for (j = i + 1; j < n; j++)
if (arr[j] > arr[minIndex])
minIndex = j;
if (minIndex != i) {
temp = arr[i];
arr[i] = arr[minIndex];
arr[minIndex] = temp;
}
}
}
bookType prototype:
class bookType{
public:
bookType();
string getTitle() const;
string getAuthor() const;
string getPublisher() const;
string getDateAdded() const;
string getISBN() const;
int getQty() const;
double getWholesale() const;
double getRetail() const;
static int getBookCount();
void setTitle(string title);
void setISBN(string ISBN);
void setDateAdded(string date);
void setAuthor(string author);
void setPublisher(string publisher);
void setQty(int qty);
void setWholesale(double wholesale);
void setRetail(double retail);
static void setBookCount(int count);
bool operator==(const bookType &other);
bool operator!=(const bookType &other);
bool operator<(const bookType &other);
bool operator<=(const bookType &other);
bool operator>=(const bookType &other);
bool operator>(const bookType &other);
void operator=(const bookType &other);
private:
string bookTitle;
string bookAuthor;
string bookPublisher;
string dateAdded;
string bookISBN;
int qtyOnHand;
double bookWholesale;
double bookRetail;
static int bookCount;
};
Overloading code
bool bookType::operator==(const bookType &other){
if (getQty() == other.getQty()) return true;
else return false;
}
bool bookType::operator!=(const bookType &other){
if (getQty() != other.getQty()) return true;
else return false;
}
bool bookType::operator<(const bookType &other){
if (getQty() < other.getQty()) return true;
else return false;
}
bool bookType::operator<=(const bookType &other){
if (getQty() <= other.getQty()) return true;
else return false;
}
bool bookType::operator>=(const bookType &other){
if (getQty() >= other.getQty()) return true;
else return false;
}
bool bookType::operator>(const bookType &other){
if (getQty() > other.getQty()) return true;
else return false;
}
void bookType::operator=(const bookType &other){
setTitle(other.getTitle());
setAuthor(other.getAuthor());
setPublisher(other.getPublisher());
setDateAdded(other.getDateAdded());
setISBN(other.getISBN());
setQty(other.getQty());
setWholesale(other.getWholesale());
setRetail(other.getRetail());
}

Related

how to fix no viable overloaded '=' in cpp

class Gebot{
string name;
int betrag;
public:
Gebot(string name, int betrag = 100) : name{name} , betrag{betrag} {
//ganze Zahl >0 und <=10.000.000
if(name.size() ==0 || betrag <=0 || betrag > 10000000)
throw runtime_error("illegal name or deposite");
}
bool selbe_bieterin(const Gebot& gebot) const{
if(gebot.name == this->name)
return true;
return false;
}
bool operator==(const Gebot& gebot) const{
name = "name";
if(gebot.betrag == this->betrag)
return true;
return false;
}
bool operator<(const Gebot& gebot) const{
if(gebot.betrag > this->betrag)
return true;
return false;
}
bool operator>=(int gebot) const{
if(gebot <= this->betrag)
return true;
return false;
}
friend ostream& operator<<(ostream& o, const Gebot & gebot){
//[Susi: 263 Euro]
o<<"["<<gebot.name<<": "<<gebot.betrag<<" Euro]";
return o;
}
};
why do I get this problemm 25:10: error: no viable overloaded '='
name = "name"; when trying to change variable name to "name". How to fix it. Thanks in advance).
This method is const
bool operator==(const Gebot& gebot) const {
^^^^^
name = "name"; <<-- changing the value of name
if(gebot.betrag == this->betrag)
return true;
return false;
}
But you are trying to change the value of name, so the code you wrote for the method is not const.
The solution would seem to be to delete the line name = "name";, it's not obvious why it is there.
BTW this code
if(gebot.betrag == this->betrag)
return true;
return false;
can be written much more simply as
return gebot.betrag == this->betrag;

Input Stream Invalid read/write of size 1

i've been absolutely lost on this topic. I wrote my own String class and tried running it in valgrind to see of it really works. Valgrind tells me that i got a lot of invalid read's and write's.
Basically what im trying to do is feed it a String Value and read it's contents later on. For this i defined following Header file.
#ifndef STRING_H_INCLUDED
#define STRING_H_INCLUDED
#include<iostream>
#include<istream>
#include<ostream>
class string{
public:
string(char* = nullptr);
~string();
string(const string&);
friend std::istream& operator>>(std::istream&,string&);
friend std::ostream& operator<<(std::ostream&,string&);
bool operator<(const string&);
bool operator==(const string&);
void setContent(char*);
char* getContent() const;
private:
unsigned getSize() const;
void copyStr(char*,char*);
unsigned getCharl(const char*)const;
string& operator=(const string&);
char* s = nullptr;
};
#endif // STRING_H_INCLUDED
The CPP for the Header looks like the following.
#include<iostream>
#include<ostream>
#include "string.h"
string::string(char* i){
if(i == nullptr){
s = new char[1];
s[0] = '\0';
}else{
s = new char[getCharl(i)+1];
copyStr(s,i);
}
}
string::~string(){
if(s != nullptr){
delete s;
}
}
unsigned string::getCharl(const char* i) const{
const char* ende = i;
for(; *ende != '\0';++ende)
;
return ende-i;
}
void string::copyStr(char* s,char* i){
unsigned index = 0;
s = new char[getCharl(i)+1];
while (i[index] != '\0'){
s[index] = i[index];
index++;
}
s[index] = '\0';
}
bool string::operator<(const string& s1){
if(getSize()<s1.getSize()){
return true;
}else if(getSize()>s1.getSize()){
return false;
}else{
for(unsigned i = 0; i < s1.getSize();++i){
if(getContent()[i] != s1.getContent()[i]){
if(getContent()[i]<s1.getContent()[i]){
return true;
}else{
return false;
}
}
}
return false;
}
}
string::string(const string& x){
delete s;
s = new char[x.getSize()];
char* tmp = x.getContent();
unsigned index = 0;
while (tmp[index] != '\0'){
this->s[index] = x.s[index];
index++;
}
}
char* string::getContent() const{
return s;
}
void string::setContent(char* v){
s = v;
}
string& string::operator=(const string& x){
if(this == &x)
return *this;
if(&x != this){
delete getContent();
setContent(nullptr);
setContent(new char[x.getSize()]);
}
copyStr(getContent(),x.getContent());
return *this;
}
bool string::operator==(const string& l){
if(getSize() == l.getSize()){
unsigned length = getSize();
for(unsigned i = 0; i < length;++i){
if(getContent()[i] != l.getContent()[i])
return false;
}
return true;
}
return false;
}
std::istream& operator>>(std::istream& is, string& arg){
return is >> arg.s;
}
std::ostream& operator<<(std::ostream& os, string& arg){
return os << arg.getContent();
}
unsigned string::getSize() const{
unsigned length = 0;
while(s[length]){
++length;
}
++length;
return length;
}
Basically i would be pretty happy to know why i get an error in my operator>> where i try to write a char* Array to my char* s.
And i would like to know why i get an error in my function getSize() in the while-loop. (Error appears at s[length]).
Maybe someone is so kind to explain me the reasons.
Cheers!
Edit:
Modified the program now to look like the following implementing the comments.
#include<iostream>
#include<ostream>
#include "string.h"
string::string(char* i){
if(i == nullptr){
s = new char[1];
s[0] = '\0';
}else{
s = new char[getCharl(i)+1];
copyStr(i);
}
}
string::~string(){
if(s != nullptr){
delete[] s;
}
}
unsigned string::getCharl(const char* i) const{
const char* ende = i;
for(; *ende != '\0';++ende)
;
return ende-i;
}
void string::copyStr(char* i){
unsigned index = 0;
delete[] s;
char* tmp = new char[getCharl(i)+1];
while (i[index] != '\0'){
tmp[index] = i[index];
index++;
}
tmp[index] = '\0';
s = tmp;
}
bool string::operator<(const string& s1){
if(getSize()<s1.getSize()){
return true;
}else if(getSize()>s1.getSize()){
return false;
}else{
for(unsigned i = 0; i < s1.getSize();++i){
if(getContent()[i] != s1.getContent()[i]){
if(getContent()[i]<s1.getContent()[i]){
return true;
}else{
return false;
}
}
}
return false;
}
}
string::string(const string& x){
copyStr(x.getContent());
}
char* string::getContent() const{
return s;
}
void string::setContent(char* v){
s = v;
}
string& string::operator=(const string& x){
if(this == &x)
return *this;
if(&x != this){
delete[] getContent();
setContent(nullptr);
setContent(new char[x.getSize()]);
}
copyStr(x.getContent());
return *this;
}
bool string::operator==(const string& l){
if(getSize() == l.getSize()){
unsigned length = getSize();
for(unsigned i = 0; i < length;++i){
if(getContent()[i] != l.getContent()[i])
return false;
}
return true;
}
return false;
}
std::istream& operator>>(std::istream& is, string& arg){
is >> arg.s;
return is;
}
std::ostream& operator<<(std::ostream& os, string& arg){
return os << arg.getContent();
}
unsigned string::getSize() const{
unsigned length = 0;
while(getContent()[length]){
++length;
}
++length;
return length;
}
Still the problem with the operator>> exists and also now im getting errors in getCharl in the for loop and copyStr im the while loop. (invalid read)
If someone would be so kind and explain to me why.

Why it's not possible to assign std::string to a subtring?

This is the code for my project which I want to compile. The error is stated at the end of the question.
#include <iostream>
#include <string>
#include <stdio.h>
class substring {
friend std::ostream& operator<<(std::ostream& output, substring const& sub);
public:
char *str;
int length;
substring();
~substring();
substring(std::string);
substring(const substring &);
substring& operator=(substring const& other);
substring& operator=(std::string const& strz);
substring& operator+=(substring const& other);
bool operator>(substring const& other) const;
bool operator<(substring const& other) const;
char& operator[](size_t idx);
char operator[](size_t idx) const;
};
std::ostream& operator<<(std::ostream& output, substring const& sub);
std::istream& operator >> (std::istream& input, substring const& sub);
bool operator==(substring const& one, substring const& another);
bool operator!=(substring const& one, substring const& another);
bool operator==(std::string const& str, substring const& sub);
bool operator==(substring const& sub, std::string const& str);
bool operator!=(std::string const& str, substring const& sub);
bool operator!=(substring const& sub, std::string const& str);
substring::substring()
{
length = 0;
}
substring::~substring()
{
delete str;
}
substring::substring(std::string)
{
}
substring::substring(const substring & sub)
{
str = new char[length];
}
std::ostream & operator<<(std::ostream & output, substring const & sub)
{
output << sub;
return output;
}
std::istream & operator >> (std::istream & input, substring const & sub)
{
std::cout << "Enter sub:";
input >> sub;
return input;
}
bool operator==(substring const & one, substring const & another)
{
if (one.length != another.length)
return false;
else
{
for (int i = 0; i < another.length; i++)
if (one[i] != another[i])
{
return false;
break;
}
}
return true;
}
bool operator!=(substring const & one, substring const & another)
{
if (one.length != another.length)
return true;
else
{
for (int i = 0; i < another.length; i++)
if (one[i] != another[i])
{
return true;
break;
}
}
return false;
}
bool operator==(std::string const & str, substring const & sub)
{
if (sub.length != str.length())
return false;
else
{
for (int i = 0; i < sub.length; i++)
if (str[i] != sub[i])
{
return false;
break;
}
}
return true;
}
bool operator==(substring const & sub, std::string const & str)
{
if (str.length() != sub.length)
return false;
else
{
for (unsigned int i = 0; i < str.length(); i++)
if (sub[i] != str[i])
{
return false;
break;
}
}
return true;
}
bool operator!=(std::string const & str, substring const & sub)
{
if (sub.length != str.length())
return true;
else
{
for (int i = 0; i < sub.length; i++)
if (str[i] != sub[i])
{
return true;
break;
}
}
return false;
}
bool operator!=(substring const & sub, std::string const & str)
{
if (sub.length != str.length())
return true;
else
{
for (int i = 0; i < sub.length; i++)
if (str[i] != sub[i])
{
return true;
break;
}
}
return false;
}
substring & substring::operator=(substring const & other)
{
delete str;
length = other.length;
str = new char[length];
for (int i = 0; i<length; i++)
{
str[i] = other.str[i];
}
return *this;
}
substring & substring::operator=(std::string const & strz)
{
length = strz.length();
str = new char[length];
for (int i = 0; i<length; i++)
{
str[i] = strz[i];
}
return *this;
}
substring & substring::operator+=(substring const & other)
{
char* new_str = new char[length + other.length];
for (int i = 0; i<length; i++)
{
new_str[i] = str[i];
}
for (int i = length; i<other.length; i++)
{
new_str[i] = other.str[i];
}
delete str;
str = new_str;
return *this;
}
bool substring::operator>(substring const & other) const
{
return true;
}
bool substring::operator<(substring const & other) const
{
return true;
}
char & substring::operator[](size_t idx)
{
return str[idx];
}
char substring::operator[](size_t idx) const
{
return str[idx];
}
int main()
{
std::string str = "abc";
substring sub = str;
std::cout << sub;
return 0;
}
The problem is that when I run this code, it seems that the compiler just skips this: substring sub = str;.
I cannot even change this line to substring sub = "aaa"; because it shows an error which says I cannot convert subtring to std::string (although there is an operation overloading for this in the code).
The problem is that when I run this code, it seems that the compiler just skips this: substring sub = str;
The compiler did not "skip it". It compiled succesfully, and the new object was created succesfully. However, the converting constructor that you defined leaves the objects members default initialized:
substring::substring(std::string)
{
}
I cannot even change this line to substring sub = "aaa"; because it shows an error which says I cannot convert subtring to std::string
I highly doubt that. I suspect that you misread.
My compiler says that const char [4] cannot be converted substring
(although there is an operation overloading for this in the code).
There certainly isn't a substring::substring(const char(&)[4]) (nor substring::substring(const char*)).

segmentation fault scrabble game

im working on a little scrabblegame which i read a txtfile and create a hashtable for all words inside. Word is a specific class which contains a vector of .
i want to create a hashmap by my own and define the length of my "Dictionary" is 50000. im using a nullpointer to reserve all index of my array. If i want to print to my hashtable, compiler tells me a segmentation fault. does any one seems the error?
the headerfile:
class Dictionary {
public:
Dictionary();
Dictionary(string filepath);
friend std::ostream& operator<<(std::ostream& os, const Dictionary& obj);
bool find(const Word& word);
vector<Word> allPossibleWords(const vector<Character>& tiles);
// struct compare {
//
// bool operator()(const Word& a, const Word& b) {
// return a.operator<(b);
// }
// } myCompare;
vector<Word> m_allWords;
vector<Word>::iterator itVecWords;
static const int table_size = 500000;
// std::array <Word*, table_size> arrWords = {nullptr};
Word* arrWords[table_size] = {nullptr};
int hash(Word new_word);
void addItem(Word word);
void printHashTable();
the cpp:
Dictionary::Dictionary(string filepath) {
ifstream datei(filepath.c_str());
while (datei.good() && !datei.eof()) {
string temp;
string temp1;
string::size_type pos;
getline(datei, temp);
pos = temp.find(" ");
temp1 = temp.substr(0, pos);
Word new_word(temp1);
addItem(new_word);
}
datei.close();
}
std::ostream& operator<<(std::ostream& os, const Dictionary& obj) {
for (int i = 0; i < obj.m_allWords.size(); i++) {
os << obj.m_allWords[i] << endl;
}
return os;
}
bool Dictionary::find(const Word& word) const {
if (std::binary_search(m_allWords.begin(), m_allWords.end(), word)) {
return true;
}
return false;
}
vector<Word> Dictionary::allPossibleWords(const vector<Character>& tiles) const {
vector<Word> ergebnis;
string tmp;
int cnt = 0;
for (int i = 0; i < tiles.size(); i++) {
tmp += tiles[i].GetC();
}
sort(tmp.begin(), tmp.end());
for (int i = 1; i <= tiles.size(); i++) {
do {
string piece = tmp.substr(0, i);
do {
Word search = Word(piece);
//Überschreibt immer der in Ergebnis existierte Wert
if (find(search) && std::find(ergebnis.begin(), ergebnis.end(), search) == ergebnis.end()) {
ergebnis.push_back(search);
}
} while (next_permutation(piece.begin(), piece.end()));
} while (next_permutation(tmp.begin(), tmp.end()));
}
return ergebnis;
}
int Dictionary::hash(Word new_word) {
int index = 0;
for (auto u : new_word.new_Character) {
index += (int) u.GetC();
}
index = index * (int) new_word.new_Character.at(0).GetC();
index = index * (int) new_word.new_Character.at(new_word.new_Character.size() - 1).GetC();
return index % table_size;
}
void Dictionary::addItem(Word word) {
int index = hash(word);
if (arrWords[index] == nullptr) {
arrWords[index] = new Word(word);
} else {
Word* ptr = arrWords[index];
Word* neu = new Word(word);
while (ptr->getNextWord() != nullptr) {
ptr = ptr->getNextWord();
}
ptr->setNextWord(neu);
}
}
void Dictionary::printHashTable() {
Word* tmp;
for (int i = 0; i < table_size; i++) {
tmp = arrWords[i];
if (tmp != nullptr) {
tmp->printWord();
cout << "Index : " << i;
}
tmp = tmp->getNextWord();
}
}
class Word {
public:
Word();
Word(string m_wort);
int length() const;
int points() const;
friend std::ostream& operator<<(std::ostream& os, const Word& obj);
bool operator==(const Word& right) const; /
bool operator!=(const Word& right) const;
bool contains(const Character& c) const;
Word substr(int start, int end) const;
bool operator<(const Word& right) const;
vector <Character> new_Character;
Word* Next = nullptr;
void setNextWord(Word*);
Word* getNextWord();
void printWord();
string getWordAsString();
CPP File:
void Word::setNextWord(Word* w) {
Next = w;
}
Word* Word::getNextWord() {
return Next;
}
void Word::printWord() {
string s = "";
for (int i = 0; i < new_Character.size(); i++) {
s += new_Character.at(i).GetC();
}
cout << s << endl;
}
string Word::getWordAsString() {
string s;
for (int i = 0; i < new_Character.size(); i++) {
s += new_Character.at(i).GetC();
}
return s;
}

Return value from overloaded operator Segmentation Fail

Got in header
DuzaLiczba operator>(const DuzaLiczba& right) const;
string& getData();
virtual ~DuzaLiczba();
private:
string& data;
In my class overloaded operators return string in "\002\994\23923\"
return DuzaLiczba(wynik);
In main
cout << dl3.getData();
cout.flush();
cout.flush throws Segmentation fail.
Return in class is in ascii?
And heres problem. Got any advice?
You should not hold a reference in your class. You held a reference to a local variable, which was destructed and then accessed causing the segmentation fault. Also, operator> and operator< return bool normally.
class DuzaLiczba {
public:
DuzaLiczba(string& input);
DuzaLiczba(const DuzaLiczba& orig);
bool operator==(const DuzaLiczba &other) const;
bool operator!=(const DuzaLiczba &other) const;
DuzaLiczba operator+(const DuzaLiczba& right) const;
DuzaLiczba operator-(const DuzaLiczba& right) const;
DuzaLiczba operator<(const DuzaLiczba& right) const;
DuzaLiczba operator>(const DuzaLiczba& right) const;
string& getData();
virtual ~DuzaLiczba();
private:
string& data;
};
And == operator
bool DuzaLiczba::operator==(const DuzaLiczba &other) const {
string liczba1 = this->data;
string liczba2 = right.data;
char index1 = liczba1.length();
char index2 = liczba2.length();
short k;
short o;
short f = 0; //przeniesienie
string wynik;
int sizefi = 0;
char temp;
int i = 0;
//"gupie" to C# RUUUULEEEZ
// http://www.youtube.com/watch?v=bXoc9hOIj3M hahahaa "D
if (liczba1.length() == liczba2.length()) { //najpierw dlugosc szybciej niz pokolei
for (i = 0; i < index1; i++) {
if (liczba1[i] == liczba2[i]) { //sprawdza kazdy element jesli sie rozni to false
wynik =
"TRUE";
} else {
wynik = "FALSE";
}
}
} else {
wynik = "FALSE";
}
return DuzaLiczba(wynik);
}
And retturn data
string& DuzaLiczba::getData() {
return data; //zwoloniony string
}
All i want to return a string.
dl1 = "123089127312890372109371203971293012903"
dl2 = "12837129037812903812903"
eg. DuzaLiczba dl3(dl1+dl2)
and cout it.
Code inside class do math great.
Or create overloader operator "<<".