Untitled

mail@pastecode.io avatar
unknown
plain_text
2 years ago
5.3 kB
5
Indexable
Never
#include<iostream>
#include<fstream>
#include<queue>
#include<stack>
#include<string>
#include<sstream>
using namespace std;

struct Card
{
	string id, name, set, type;
	bool collectible;
	int mana, attack, health, armor;
};

struct Node {
	Card data;
	Node* left, * right;
};

void Init(Node*& root)
{
	root = NULL;
}

Node* CreatNode(Card value)
{
	Node* p = new Node;
	if (p == NULL)
	{
		cout << "\nnot enough memory !";
		return NULL;
	}

	p->data = value;
	p->left = p->right = NULL;
	return p;
}

void LL(Node*& pRoot)
{
	Node* p = pRoot->right;
	pRoot->right = p->left;
	p->left = pRoot;
	pRoot = p;
}

void RR(Node*& pRoot)
{
	Node* p = pRoot->left;
	pRoot->left = p->right;
	p->right = pRoot;
	pRoot = p;
}

int Height(Node* pRoot) {
	if (pRoot == NULL)
		return 0;
	return max(Height(pRoot->left), Height(pRoot->right)) + 1;
}

void balance(Node*& pRoot)
{
	int bal = Height(pRoot->left) - Height(pRoot->right);

	if (bal > 1) // Cây lệch trái
	{
		if (Height(pRoot->left->left) >= Height(pRoot->left->right)) //Cây lệch trái trái
			RR(pRoot);
		if (Height(pRoot->left->left) < Height(pRoot->left->right)) { //Cây lệch trái phải
			LL(pRoot->left);
			RR(pRoot);
		}
	}

	if (bal < -1) { //Cây lệch phải
		if (Height(pRoot->right->right) >= Height(pRoot->right->left)) //Cây lệch phải phải
			LL(pRoot);
		if (Height(pRoot->right->right) < Height(pRoot->right->left)) { //Cây lệch phải trái
			RR(pRoot->right);
			LL(pRoot);
		}
	}
}

void Insert_ID(Node*& pRoot, Node* p)
{
	if (pRoot == NULL)
	{
		pRoot = p;
	}

	if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) < 0)
	{
		Insert_ID(pRoot->right, p);
	}
	else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) > 0)
	{
		Insert_ID(pRoot->left, p);
	}
	else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) == 0)
		return;

	balance(pRoot);
}

void Insert_Mana_Health_ID(Node*& pRoot, Node* p)
{
	if (pRoot == NULL)
	{
		pRoot = p;
		return;
	}

	if (pRoot->data.mana < p->data.mana)
	{
		Insert_ID(pRoot->right, p);
	}
	else if (pRoot->data.mana > p->data.mana)
	{
		Insert_ID(pRoot->left, p);
	}
	else
	{
		if (pRoot->data.health < p->data.health)
		{
			Insert_ID(pRoot->right, p);
		}
		else if (pRoot->data.health > p->data.health)
		{
			Insert_ID(pRoot->left, p);
		}
		else
		{
			if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) < 0)
			{
				Insert_ID(pRoot->right, p);
			}
			else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) > 0)
			{
				Insert_ID(pRoot->left, p);
			}
			else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) == 0)
				return;
		}
	}

	balance(pRoot);
}

void Insert_HealthAttack_Mana_ID(Node*& pRoot, Node* p)
{
	if (pRoot == NULL)
	{
		pRoot = p;
		return;
	}

	if (pRoot->data.health + pRoot->data.attack < p->data.health+p->data.attack)
	{
		Insert_ID(pRoot->right, p);
	}
	else if (pRoot->data.health + pRoot->data.attack > p->data.health + p->data.attack)
	{
		Insert_ID(pRoot->left, p);
	}
	else
	{
		if (pRoot->data.mana < p->data.mana)
		{
			Insert_ID(pRoot->right, p);
		}
		else if (pRoot->data.mana > p->data.mana)
		{
			Insert_ID(pRoot->left, p);
		}
		else
		{
			if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) < 0)
			{
				Insert_ID(pRoot->right, p);
			}
			else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) > 0)
			{
				Insert_ID(pRoot->left, p);
			}
			else if (strcmp(pRoot->data.id.c_str(), p->data.id.c_str()) == 0)
				return;
		}
	}

	balance(pRoot);
}

void CreateTreeAVL(Node*& Root, string filename, int luachon)
{
	Init(Root);

	ifstream ifs(filename);
	if (!ifs.is_open())
	{
		cout << "\ncannot find file";
		return;
	}

	string ignore = "";
	getline(ifs, ignore);

	while (!ifs.eof())
	{
		Card c;
		getline(ifs, c.id, ';');
		getline(ifs, c.name, ';');
		getline(ifs, c.set, ';');
		getline(ifs, c.type, ';');

		string check = "";
		getline(ifs, check, ';');
		if (strcmp(check.c_str(), "True") == 0)
		{
			c.collectible = true;
		}
		else if (strcmp(check.c_str(), "False") == 0)
		{
			c.collectible = false;
		}

		ifs >> c.mana;
		ifs >> c.attack;
		ifs >> c.health;
		ifs >> c.armor;

		Node* p = CreatNode(c);

		if (luachon == 1) // lựa chọn số 1: duyệt theo ID
		{
			Insert_ID(Root, p);
		}
		else if (luachon == 2) // lựa chọn số 2: duyệt theo Mana->Health->ID
		{
			Insert_Mana_Health_ID(Root, p);
		}
		else if (luachon == 3) // lựa chọn số 3: duyệt theo attack + health → mana → ID.
		{
			Insert_HealthAttack_Mana_ID(Root, p);
		}
	}

	ifs.close();
}

void LNR(Node* pRoot)
{
	if (pRoot != NULL)
	{
		LNR(pRoot->left);
		cout << "\n"<< pRoot->data.id << " ";
		cout << pRoot->data.name<< " ";
		cout << pRoot->data.set << " ";
		cout << pRoot->data.type << " ";
		cout << pRoot->data.collectible << " ";
		cout << pRoot->data.mana << " ";
		cout << pRoot->data.attack << " ";
		cout << pRoot->data.health << " ";
		cout << pRoot->data.armor << endl;;

		LNR(pRoot->right);
	}
}

int main()
{
	Node* pRoot = NULL;
	CreateTreeAVL(pRoot, "sample_patch1.txt", 1);
	LNR(pRoot);
	return 0;
}