Extending the Fuzzy Set

Status
Not open for further replies.

Baljeet

Member
Jan 31, 2011
76
0
Having a based on a string is nice, but sometimes you want it to be based on an integer, float, or something else. To accomplish this, we'll extend the string-based fuzzy set class to a template.

First, we'll modify fset.h and fset.cpp into the following fsett.h (I couldn't get the test program to compile with them seperate):
Code:
#ifndef FSETT_DEFINED
#define FSETT_DEFINED

#include "fbool.h"
#include <map>

template<class T> class Fset
{
  std::map<T,Fbool> setdata;
public:
  void insert(const T, const double);
  void insert(const T, const bool);
  int size();
  bool empty();
  void erase(T);
  void clear();
  Fset<T> operator&&(Fset<T>);
  Fset<T> operator||(Fset<T>);
  Fset<T> operator!();
  Fbool& operator[](T);
};

template<class T> void Fset<T>::insert(const T key, const double prob)
{
  Fset<T>::setdata.insert(std::pair<T,Fbool>(key,prob));
}

template<class T> void Fset<T>::insert(const T key, const bool prob)
{
  Fset<T>::setdata.insert(std::pair<T,Fbool>(key,prob));
}

template<class T> int Fset<T>::size()
{
  return Fset<T>::setdata.size();
}

template<class T> bool Fset<T>::empty()
{
  return Fset<T>::setdata.empty();
}

template<class T> void Fset<T>::erase(T key)
{
  Fset<T>::setdata.erase(key);
}

template<class T> void Fset<T>::clear()
{
  Fset<T>::setdata.clear();
}

template<class T> Fset<T> Fset<T>::operator&&(Fset<T> operand)
{
  Fset<T> temp;
  Fbool temp2;
  typename std::map<T,Fbool>::iterator pos1;
  typename std::map<T,Fbool>::iterator pos2;
  for (pos1 = this->setdata.begin(), pos2 = operand.setdata.begin(); pos1 != this->setdata.end() && pos2 != operand.setdata.end();)
  {
    if (pos1->first < pos2->first)
    {
      temp2.setval(false);
      temp.insert(pos1->first,temp2.getval());
      ++pos1;
    }
    else if (pos1->first > pos2->first)
    {
      temp2.setval(false);
      temp.insert(pos2->first,temp2.getval());
      ++pos2;
    }
    else
    {
      temp.insert(pos2->first,((pos1->second)&&(pos2->second)).getval());
      ++pos1;
      ++pos2;
    }
  }
  return temp;
}

template<class T> Fset<T> Fset<T>::operator||(Fset<T> operand)
{
  Fset<T> temp;
  typename std::map<T,Fbool>::iterator pos1;
  typename std::map<T,Fbool>::iterator pos2;
  for (pos1 = this->setdata.begin(), pos2 = operand.setdata.begin(); pos1 != this->setdata.end() && pos2 != operand.setdata.end();)
  {
    if (pos1->first < pos2->first)
    {
      temp.insert(pos1->first,(pos1->second).getval());
      ++pos1;
    }
    else if (pos1->first > pos2->first)
    {
      temp.insert(pos2->first,(pos2->second).getval());
      ++pos2;
    }
    else
    {
      temp.insert(pos2->first,((pos1->second)||(pos2->second)).getval());
      ++pos1;
      ++pos2;
    }
  }
  return temp;
}

template<class T> Fset<T> Fset<T>::operator!()
{
  Fset<T> temp;
  typename std::map<T,Fbool>::iterator pos1;
  for (pos1 = this->setdata.begin(); pos1 != this->setdata.end();++pos1)
  {
    temp.insert(pos1->first,(!(pos1->second)).getval());
  }
  return temp;
}

template<class T> Fbool& Fset<T>::operator[](T key)
{
  return Fset<T>::setdata[key];
}

#endif

Most of this is a fairly straightforward modification. It is worth noting, however, that you MUST add the typename keyword in front of the iterators. Also, you have to add the template<class T> keyword in front of each function definition.

We can test this template with the following testfsett.cpp:
Code:
#include "fsett.h"
#include <iostream>
#include <string>
using std::string;
using std::cout;

int main(int argc,char* argv[])
{
  Fset<int> myintset;
  cout<<"myintset.empty = "<<myintset.empty()<<"\n";
  cout<<"myintset.count = "<<myintset.size()<<"\n";
  myintset.insert(0,false);
  myintset.insert(1,true);
  myintset.insert(2,0.33);
  myintset.insert(3,0.5);
  cout<<"myintset.empty = "<<myintset.empty()<<"\n";
  cout<<"myintset.count = "<<myintset.size()<<"\n";

  Fset<string> mytestset;
  cout<<"mytestset.empty = "<<mytestset.empty()<<"\n";
  cout<<"mytestset.count = "<<mytestset.size()<<"\n";
  mytestset.insert("false",false);
  mytestset.insert("true",true);
  mytestset.insert("third",0.33);
  mytestset.insert("half",0.5);
  cout<<"mytestset.empty = "<<mytestset.empty()<<"\n";
  cout<<"mytestset.count = "<<mytestset.size()<<"\n";

  Fset<string> mytest2;
  mytest2.insert("false",true);
  mytest2.insert("true",false);
  mytest2.insert("quarter",0.25);
  mytest2.insert("half",0.5);
  cout<<"mytest2.empty = "<<mytest2.empty()<<"\n";
  cout<<"mytest2.count = "<<mytest2.size()<<"\n";

  Fset<string> andset = mytest2&&mytestset;
  Fset<string> orset = mytest2||mytestset;
  Fset<string> notset = !mytestset;

  cout<<"andset[\"false\"] = "<<andset["false"].getval()<<"\n";
  cout<<"orset[\"false\"] = "<<orset["false"].getval()<<"\n";
  cout<<"notset[\"false\"] = "<<notset["false"].getval()<<"\n";
  return 0;
}

Compiling this with g++ testfsett.cpp fbool.cpp -o testfsett produces the following output:
Code:
myintset.empty = 1
myintset.count = 0
myintset.empty = 0
myintset.count = 4
mytestset.empty = 1
mytestset.count = 0
mytestset.empty = 0
mytestset.count = 4
mytest2.empty = 0
mytest2.count = 4
andset["false"] = 0
orset["false"] = 1
notset["false"] = 1

Note: I was not able to split the fsett.h into an fsett.h and fsett.cpp and compile using: g++ testfsett.cpp fsett.cpp fbool.cpp -o testfsett without getting errors. If anyone wants to suggest corrections, feel free to add them.

All Credits goes to one who really made this...
 
Status
Not open for further replies.

Users who are viewing this thread

Top