并不优雅的背包算法

白昼怎懂夜的黑 提交于 2020-01-18 15:41:40

问题描述:有若干物品,物品的质量和体积已知。有一个容积固定的背包,怎样在背包中装入质量尽可能大的物品

代码如下,注释应该足够详细,只是代码风格不太优雅(捂脸)

#include<iostream>
#include<vector>

using namespace std;

//用来定义物品,需要提供质量和体积
class BagObj
{
public:
	bool isSelected = false;//物品是否被选中
	int quality = 0;//质量
	int volume = 0;//体积

	//传入体积和质量
	BagObj(int fromVol, int fromQua);
};

BagObj::BagObj(int fromVol, int fromQua)
{
	quality = fromQua;
	volume = fromVol;
}

class BagHandle
{
private:
	int objNum = 0;//物品的总数
	int bagVol = 0;//背包的体积
	vector<BagObj> objList;//物品的属性列表

	int bagProblemDealCore(int restVol,//剩余的背包体积
		vector<BagObj>::iterator fromIter//物品开始迭代的位置
		);
public:
	//需要用户输入相关信息
	BagHandle();//没有传入参数的构造函数

	void bagDeal();//开始处理背包问题
	void resultOutput();//输出结果
};

BagHandle::BagHandle()
{
	//获取背包属性
	cin >> bagVol;
	//获取用户输入
	cin >> objNum;

	//循环获取每个物品的参数
	for (int i = 0; i < objNum; ++i)
	{
		int tempQua = 0;//用于输入的质量
		int tempVol = 0;//用于输入的体积
		cin >> tempQua >> tempVol;

		//将新建的物品对象加入到列表
		objList.push_back(BagObj(tempVol, tempQua));
	}
}

//用递归的方式解决问题
void BagHandle::bagDeal()
{
	//新建列表的迭代器
	vector<BagObj>::iterator iter = objList.begin();

	//将参数传入到递归函数
	bagProblemDealCore(bagVol, iter);
}

void BagHandle::resultOutput()//输出算法处理的结果
{
	cout << "体积\t质量" << endl;
	int qualitySum = 0;
	//迭代处理结果
	for (vector<BagObj>::iterator iter = objList.begin();
		iter != objList.end(); ++iter)
	{
		//判断物品是否被选中
		if (iter->isSelected)
		{
			//输出物品信息
			cout << iter->volume << "\t" << iter->quality << endl;
			//计算总的质量
			qualitySum += iter->quality;
		}
	}
	//输出总的质量
	cout << qualitySum << endl;
}

int BagHandle::bagProblemDealCore(int restVol,//剩余的背包体积
	vector<BagObj>::iterator fromIter//物品开始迭代的位置
)
{
	//判断迭代结束的条件
	if (fromIter == objList.end())
		return 0;

	//判断当前物品能否被选取
	if (fromIter->volume > restVol)
	{
		fromIter->isSelected = false;
		//继续下一次迭代
		return bagProblemDealCore(restVol, fromIter + 1);
	}

	//分别比较选与不选
	int selectedResult = bagProblemDealCore(restVol - fromIter->volume,
		fromIter + 1) + fromIter->quality;
	int unSelectedResult = bagProblemDealCore(restVol, fromIter + 1);

	//如果选取
	if (selectedResult > unSelectedResult)
	{
		fromIter->isSelected = true;
		//选取的情形需要再次被执行,为了修正isselected
		return bagProblemDealCore(restVol - fromIter->volume,
			fromIter + 1) + fromIter->quality;
	}

	else
	{
		fromIter->isSelected = false;
		return unSelectedResult;
	}
}


int main()
{
	BagHandle tempBag;
	tempBag.bagDeal();
	tempBag.resultOutput();
    return 0;
}

 

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!