Esempio n. 1
0
void DFS(int idx) {
	if(idx == 4) {
		toCheck();
		return;
	}
	for(int i = 1; i <= 6; i++) {
		A[idx] = i;
		DFS(idx+1);
	}
}
int main(int argc, char *argv[])
{
	char *filename;
	if (argc > 1)
		filename = argv[1];
	else
		filename = strdup("mallas/mask2.off");

	try
	{
		///////////////////////////////////////////////////////////////////////
		//Read a mesh and write a mesh
		EdgeMesh mesh1;
		cout << "Loading file " << filename << endl;
		mesh1.readFileOFF(filename, false);

		cout << "Num vertex: " << mesh1.numVertex() << "\nNum triangles: " << mesh1.numTriangles()
			<< "\nUnreferenced vertex: " << mesh1.checkUnreferencedVertex() << endl;


		///////////////////////////////////////////////////////////////////////

		//Compute the list of edges
		//TODO 2.1: 
		//Implement the body of the EdgeMesh::updateEdgeLists() method
		//Buscamos las aristas frontera
		mesh1.updateEdgeLists();

		cout << mesh1.externalEdges.size() << " boundary edges" << endl;
		cout << mesh1.internalEdges.size() << " internal edges" << endl;

		//Write external boundary
		if (mesh1.externalEdges.size() != 0)
		{
			cout << "Edges in the boundary:" << endl;
			for (auto itt = mesh1.externalEdges.begin(); itt != mesh1.externalEdges.end(); ++itt)
				cout << "[" << itt->a << "->" << itt->b << "] ";
			cout << endl;


			//Vector to store the distance from a vertex to the nearest vertex in the boundary
			std::vector<float> boundDist(mesh1.numVertex(), INFINITY);

			//TODO 2.2:
			//Compute the distance from each vertex to the boundary (measured along edges)
			//and store it in the boundDist vector

			//Calculamos las distancias entre los vértices que comparten aristas internas
			//y los vecinos de cada uno
			mesh1.updateNeighbours();

			//Fijamos la distancia de los vértices de la frontera a 0
			for (int i = 0; i < mesh1.externalEdges.size(); i++)
				boundDist[mesh1.externalEdges[i].a] = 0;

			vector<bool> toCheck(mesh1.numVertex(), false); //Indica los vértices a chequear
			bool flag = false; //Indica si se ha encontrado un camino más óptimo para un vértice
			float dist; //distancia
			int checking = -1; //índice de l vértice que se está chequeando
			int count = 0; //Número de vértices a chequear
			int neigh; //vecino

			//Rellenamos la lista de vértices a calcular o chequear
			for (int i = 0; i < mesh1.numVertex(); i++)
			{
				if (boundDist[i] == INFINITY) {
					toCheck[i] = true;
					count++;
				}
			}

			//Calculamos las distancias
			while (count > 0) //Mientras queden vértices por chequear
			{
				//Buscamos el siguiente vértice a chequear
				do
				{
					checking++;
					if (checking >= mesh1.numVertex())
						checking = 0;
				} while (!toCheck[checking]);

				//Calculamos la distancia desde cada vecino si es posible (no está a infinita distancia de la frontera)
				for (int i = 0; i < mesh1.neighbours[checking].size(); i++)
				{
					neigh = mesh1.neighbours[checking][i];
					if (mesh1.internalDistances[checking][neigh] != INFINITY && boundDist[neigh] != INFINITY)
					{
						dist = mesh1.internalDistances[checking][neigh] + boundDist[neigh];
						if (dist < boundDist[checking])
						{
							boundDist[checking] = dist;
							flag = true;
						}
					}
				}	
				
				if (boundDist[checking] != INFINITY)
				{
					if (flag) //Si se ha encontrado un camino más óptimo 
					{
						for (int i = 0; i < mesh1.neighbours[checking].size(); i++)
						{
							neigh = mesh1.neighbours[checking][i];
							if ((mesh1.internalDistances[checking][neigh] != INFINITY) && !toCheck[neigh] && boundDist[neigh]>0)
							{
								toCheck[neigh] = true;
								count++;
							}
						}
						flag = false;
					}
					toCheck[checking] = false;
					count--;
				}
			}
			//END TODO 2.2

			//Search the max distance to boundary
			float maxDistance = *(std::max_element(boundDist.begin(), boundDist.end()));
			cout << "maxDistance: " << maxDistance << endl;

			//Dump distances to boundary
			if (boundDist.size() < 20)
			{
				cout << "Distances to boundary: " << endl;
				//Dump distances to boundary
				for (size_t i = 0; i < boundDist.size(); i++)
				{
					cout << "vertex: " << i << " distance: " << boundDist[i] << endl;
				}
				cout << endl;
			}

			//TODO 2.3:
			//Create a colorMesh where the color of each vertex show the distance to boundary
			//To create colors, use the function setTemperature(1.0-boundDist[i]/maxDistance)
			//Save to file named "output_boundary.obj"
			//Visualize it with meshlab
			ColorMesh colorMesh;
			cout << "\n\n";
			cout << "Loading file " << filename << endl;
			colorMesh.readFileOFF(filename);

			for (size_t i = 0; i < colorMesh.numVertex(); i++)
			{
				colorMesh.colors[i].setTemperature(1.0 - boundDist[i] / maxDistance);
			}

			string objFilename = "output_boundary.obj";
			cout << "Saving output to " << objFilename << endl;
			colorMesh.writeFileOBJ(objFilename);

			//Visualize the .obj file with an external viewer
#ifdef WIN32
			string viewcmd = "C:/MeshLab/meshlab_32.exe";
#else
			string viewcmd = "meshlab";
#endif
			string cmd = viewcmd + " " + objFilename;
			cout << "Executing external command: " << cmd << endl;
			system(cmd.c_str());
			//END TODO 2.3

		}
	}
	catch (const string &str) { std::cerr << "EXCEPTION: " << str << std::endl; }
	catch (const char *str) { std::cerr << "EXCEPTION: " << str << std::endl; }
	catch (std::exception& e) { std::cerr << "EXCEPTION: " << e.what() << std::endl; }
	catch (...) { std::cerr << "EXCEPTION (unknow)" << std::endl; }

#ifdef WIN32
	cout << "Press Return to end the program" << endl;
	std::cin.get();
#else
#endif

	return 0;
}
/**
* @brief Checks the selected predecessor of the exit node of @c cfg.
*
* @return @c true if the next exit node's predecessor should be checked, @c
*         false otherwise. If @c false is returned, it means that no variables
*         from storedGlobalVars can be marked as 'never modified'.
*
* This function checks that every variable from @c storedGlobalVars is
* retrieved its original value before the node exits.
*/
bool OptimFuncInfoCFGTraversal::checkExitNodesPredecessor(ShPtr<CFG::Node> node) {
	if (node == cfg->getEntryNode()) {
		// We have reached the entry node.
		return false;
	}

	auto currStmtRIter = node->stmt_rbegin();
	ASSERT_MSG(currStmtRIter != node->stmt_rend(), "encountered an empty node");
	ShPtr<Statement> currStmt = *currStmtRIter;

	// Before every return, there should be a sequence
	//
	//    globalVar1 = localVar1
	//    globalVar2 = localVar1
	//    ...
	//
	// where globalVarX is a key in storedGlobalVars and localVarsX is the
	// corresponding value.
	//
	// If some global variable before a return statement is not retrieved
	// its original value, then this variable cannot be marked as 'never
	// modified'.

	// Check whether there is a statement to be skipped. We currently skip
	// just return statements.
	// TODO Skip also other statements?
	if (isa<ReturnStmt>(currStmt) && ++currStmtRIter != node->stmt_rend()) {
		currStmt = *currStmtRIter;
	}

	// Check all variables from storedGlobalVars.
	VarToVarMap toCheck(storedGlobalVars);
	while (currStmtRIter != node->stmt_rend() && isa<AssignStmt>(currStmt)) {
		ShPtr<AssignStmt> assignStmt = cast<AssignStmt>(currStmt);
		ShPtr<Variable> lhs(cast<Variable>(assignStmt->getLhs()));
		ShPtr<Expression> rhs(assignStmt->getRhs());

		// If the left-hand side is not a variable or there are some
		// function calls or dereferences, stop the check.
		ShPtr<ValueData> rhsData(va->getValueData(rhs));
		if (!lhs || rhsData->hasCalls() || rhsData->hasDerefs()) {
			break;
		}

		// Check whether the statement is of the form globalVar = localVar,
		// where globalVar is a variable from toCheck and localVar its
		// corresponding local variable.
		auto lhsFoundIter = toCheck.find(lhs);
		if (lhsFoundIter != toCheck.end() && lhsFoundIter->second == rhs) {
			toCheck.erase(lhsFoundIter);
		}

		// Move to the "next" (i.e. previous) statement (if any).
		if (++currStmtRIter != node->stmt_rend()) {
			currStmt = *currStmtRIter;
		}
	}

	// If toCheck contains some variables at this moment, they cannot be
	// marked as 'never modified'.
	for (const auto &p : toCheck) {
		storedGlobalVars.erase(p.first);
	}

	// The checking should continue only if there are still some variables that
	// can possibly be marked as 'never modified'.
	return !storedGlobalVars.empty();
}