Estas en la quinta lección del curso de sistemas expertos con Qt, y ahora implementaremos una nueva clase llamada PROPTreeBuilder.

El principal objetivo de implementar un PROPTreeBuilder es el de crear un interfaz para crear y conectar nodos para  construir un árbol semántico.

Ahora crearemos otra clase y la llamaremos PROPTreeBuilder.

Debemos de comenzar con la declaración, añadiendo los headers que nuestra clase va a usar.

Estos headers son definiciones de contenedores de Qt similares a STL, si tienes alguna duda acerca de contenedores y STL, puedes preguntar en los comentarios.


#include
#include
#include
#include "propnode.h"

Después, nuestros datos deben de ser una lista de todos los nodos presentes en el árbol, una lista de los símbolos de los nodos en el árbol,una asociación de los símbolos para obtener las entradas del árbol (que son números que especifican donde esta tal nodo), y una asociación de entradas que nos dan símbolos, estos contenedores pueden ser de utilidad en posteriores ocasiones.


QList m_lstTree;
QList m_lstSymbol;
QMap m_mapSymbol2Entry;
QMap m_mapEntry2Symbol;

Ahora, vamos a definir una función que nos permita crear un nuevo nodo y añadirlo en el árbol, Además , implementaremos una función accesor que nos permita obtener el valor del nodo usando su símbolo como llave.


PROPTreeBuilder()=default;
size_t atom(QString string);
size_t Not(int first);
size_t If(int first,int second);
size_t And(int first, int second);
size_t Iff(int first,int second);
size_t Or(int first, int second);
size_t True();
Int valueAtomBySymbol(QString symbol);
QMap getMapSymbolEntry(){return this->m_mapSymbol2Entry;}
QMap getMapEntrySymbol(){return this->m_mapEntry2Symbol;}
QList getTree()const{return this->m_lstTree;}
QList getSymbols()const{return this→m_lstSymbol;}

En el constructor del PROPTreeBuilder deberemos de limpiar los principales contenedores. Mientras que la función atom() crea un nuevo nodo y lo pone en el árbol, si ya existe omitimos la creación. Las demás funciones que crean nodos de las operaciones, realizan un procedimiento similar pero no realizan una verificación de existencia como lo hace la función atom().


PROPTreeBuilder::PROPTreeBuilder()
{
m_lstTree.clear();
m_lstSymbol.clear();
}

size_t PROPTreeBuilder::atom(QString strId){
auto it=m_mapSymbol2Entry.find(strId);
if(it != m_mapSymbol2Entry.cend())
return it.value();
else{
m_mapSymbol2Entry.insert(strId,m_lstTree.size());
m_mapEntry2Symbol.insert(m_lstTree.size(),strId);
m_lstTree.push_back(PROPNode(PROPNode::ATOM,m_lstSymbol.size(),-1));
m_lstSymbol.push_back(strId);
return m_lstTree.size()-1;
}
}

size_t PROPTreeBuilder::Not(int first){
m_lstTree.push_back(PROPNode(PROPNode::NOT,first,-1));
return m_lstTree.size()-1;
}
size_t PROPTreeBuilder::And(int first, int second){
m_lstTree.push_back(PROPNode(PROPNode::AND,first,second));
return m_lstTree.size()-1;
}
size_t PROPTreeBuilder::If(int first, int second){
m_lstTree.push_back(PROPNode(PROPNode::IF,first,second));
return m_lstTree.size()-1;
}
size_t PROPTreeBuilder::Iff(int first, int second){
m_lstTree.push_back(PROPNode(PROPNode::IFF,first,second));
return m_lstTree.size()-1;
}
size_t PROPTreeBuilder::Or(int first, int second){
m_lstTree.push_back(PROPNode(PROPNode::OR,first,second));
return m_lstTree.size()-1;
}
size_t PROPTreeBuilder::True(){
m_lstTree.push_back((PROPNode(PROPNode::TRUE,-1,-1)));
return m_lstTree.size()-1;
}

Por ultimo implementamos una función que retorna la entrada del nodo en el arbol por medio de  su simbolo (literal):


int PROPTreeBuilder::valueAtomBySymbol(QString symbol){
if(m_mapSymbol2Entry.contains(symbol))
return m_mapSymbol2Entry.value(symbol);
return -1;
}

En el siguiente video puedes observar todo este procedimiento:

Terminamos este artículo, recuerda: preguntas en comentarios, compartir si te gusto y visita nuestras redes sociales.

Leave a Reply

Your email address will not be published.