Program design thinking Week2- jobs

Program design thinking Week2- jobs

A-Maze

Problem Description

Enter a 5x5 two-dimensional array of 1s and 0s, the position representation of FIG. Map display, 0 can walk, 1 can not go, the starting point is the upper left corner, lower right corner is the end, these two positions to ensure zero. Write a program to find the shortest route starting point to the end point.
Several lines required output, represents the shortest path from upper left to lower right corner coordinates sequentially passes. Ensure data has a unique solution.

Solution analysis

The problem is typical of the BFS algorithm. Since the subject of the request shortest path sequentially through output coordinates to define an array of a path for the recording route Point class, VIS array whether a point has been traversed to the records. In the expansion process, each point may be extended to the four directions, but it should be noted that here, the BFS process not every point is traversed on the shortest path, and therefore in the definition of class Point when the need for additional pre recording position reaches the point on the path prior to the point in its path array.
Kept expanding until it reaches the end, the use of forward end of the pre recursive find the shortest path and output coordinates.

to sum up

Simple variation of this problem belongs to the BFS algorithm requires proficiency in the basic structure of the BFS.
have to be aware of is:

  1. BFS is extended through all reachable points, but not many other points on the shortest path between two points, so these records should point to go back to that point before him.
  2. The position of each point in the path array is determined, needs to front, end, front for determining the position of the point before that point, end point position of the array for recording
  3. Traversing determination condition: coordinate it should not exceed 5x5 and may not yet be traversed to reach a point. After traversing the time to stop the expansion to the finish.

Code

#include <iostream>
#include<queue>
using namespace std;
bool vis[5][5];
int a[5][5];

struct point {
	int x;
	int y;
	int pre;
	point() { }
	point(int a, int b) {
		x = a; y = b;
	}
	point(int a, int b, int p) {
		x = a; y = b; pre = p;
	}

};

queue<point> Q;
int dx[] = { 0,0,1,-1 };
int dy[] = { 1,-1,0,0 };
point path[25];
//回溯
void print(point n) {
	if (n.pre != -1)print(path[n.pre]);
	printf("(%d, %d)\n", n.x, n.y);
}

void bfs() {
	memset(vis, 0, sizeof(vis));
	int front = 0, end = 0;
	Q.push(point(0, 0,-1));
	point next,now;
	vis[0][0] = 1;
	path[end++] = point(0, 0,-1);
	while (!Q.empty()) {
		now = Q.front();
		Q.pop();
		front++;
		if (now.x == 4 && now.y == 4) {
			print(now); return;
		}
		//int count = 0;
		for (int i = 0; i < 4; ++i) {
			int x = now.x + dx[i], y = now.y + dy[i];
			if (x < 0 || x>4 || y < 0 || y>4 || a[x][y] == 1)continue;
			else if (!vis[x][y]) {
				vis[x][y] = 1;
				next.x = x, next.y = y;
				next.pre = front - 1;		//记录前一个节点
				path[end++] = next;
				Q.push(next);
			}
			
		}
	}


}

int main()
{
	for (int i = 0; i < 5; i++)
		for (int j = 0; j < 5; j++)
		{
			cin >> a[i][j];
		}
	bfs();

}

B-For Water

Problem Description

Pour problem: two cups, respectively, the maximum capacity of A and B, in the initial two cups are empty, we hope to obtain a water capacity of C by a series of operations. Operation is limited to: filling the A / B cup emptied A / B cup, poured into water A B or vice versa.
Each operation to obtain the required output volume of water C, "fill A" represents A filling cups, "empty A" represents A cup emptied, "pour AB" A represents the water poured into the cup B and the filling the cup B A or emptied. C until a volume of water, the output of "success".
ps: the answer to this question may exist multiple solutions

Solution analysis

Since the subject of the request output of each step operation, so we need to customize Status classes, including the sequence number corresponding to the specific operation of this operation and the volume of water in the cup A and B. Similar to the maze, we can start from state to obtain a series of operations for the water capacity of the C as a path that we need to find a path to successfully reach the end, and there may be multiple paths, so you can use BFS algorithm is extended to several different spreading direction of operation. The same is not extended out each step of the operation can finally get the results you want, it is necessary from an array of records each class map corresponding relationship between a state before a state.
Use BFS queue in the expansion process, discussed depending on the operation until the desired result. Recursively to an initial state according to an operation output number according to the specific operation from the array.

to sum up

The implicit question belongs to FIG problem can also be extended by BFS, need to master the basic structure of the BFS.
Need some attention:

  1. For each state is a state corresponding to only one precursor, i.e., a state in which the class map as not corresponding to the plurality of Key Value
  2. Not every state will eventually get the desired results, and therefore should be back in the state to meet these points before he then continued to other extensions that abandon useless operation.

Code

#include <iostream>
#include<string>
#include <map>
#include<queue>
using namespace std;

struct Status
{
	int a, b,m;
	bool operator<(const Status &s) const
	{
		return a != s.a ? a < s.a : b < s.b;
	}
};
queue<Status> Q;
map<Status, Status> from;

void print(Status &s) {
	if (s.m == -2)return;
	print(from[s]);
	if (s.m == 1)printf("empty A\n");
	else if(s.m==2)printf("empty B\n");
	else if(s.m==3)printf("fill A\n");
	else if (s.m == 4||s.m==5)printf("pour B A\n");
	else if (s.m == 6)printf("fill B\n");
	else if (s.m == 7||s.m==8)printf("pour A B\n");

}

void refresh(Status &s, Status &t) {
	if (from.find(t) == from.end()) {
		from[t] = s;
		Q.push(t);
	}
}

void bfs(int A, int B, int C)
{
	Status s, t;
	s.a = 0; s.b = 0; s.m = -2;
	Q.push(s);

	while (!Q.empty())
	{
		s = Q.front();
		Q.pop();
		if (s.a == C || s.b == C) {
			
			print(s); 
			printf("success\n");
			return;
		}
		//倒空a的水
		if (s.a > 0) {
			t.a = 0;
			t.b = s.b;
			t.m = 1;
			refresh(s, t);
		}
		//倒空b的水
		if (s.b > 0) {
			t.b = 0;
			t.a = s.a;
			t.m = 2;
			refresh(s, t);
		}
		//续满a
		if (s.a < A)
		{
			t.a = A;
			t.b = s.b;
			t.m = 3;
			refresh(s, t);

			if (s.b != 0) {
				if (s.a + s.b <= A) {
					t.a = s.a + s.b;
					t.b = 0;
					t.m = 4;
					refresh(s, t);
				}
				else {
					t.a = A;
					t.b = s.a + s.b - A;
					t.m = 5;
					refresh(s, t);
				}
			}
		}

		//续满b
		if (s.b < B)
		{
			t.a = s.a;
			t.b = B;
			t.m = 6;
			refresh(s, t);
			if (s.a != 0)
			{
				if (s.a + s.b <= B)
				{
					t.a = 0;
					t.b = s.a + s.b;
					t.m = 7;
					refresh(s, t);
				}
				else {
					t.a = s.a + s.b - B;
					t.b = B;
					t.m = 8;
					refresh(s, t);
				}
			}
		}

	}
	//printf("-1/n");
}


int main()
{
	int a, b, c;
	while (cin >> a >> b >> c)
	{
		bfs(a, b, c);
	}
	return 0;
}


Published 21 original articles · won praise 5 · Views 789

Guess you like

Origin blog.csdn.net/weixin_44578615/article/details/104653496