⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 visit.java

📁 大厦游览图,通过命令行来实现 System.out.println("where 显示当前在什么地方") System.out.println("list 列出当前位置的物品") S
💻 JAVA
字号:
package xiang;

import java.io.IOException;
import java.util.*;

/**
 * class Visit 用来处理人机交互的命令
 * 
 */
public class Visit {

	protected Spot location;// 当前所在地点

	protected Building bd = new Building();

	/* 地点描述 Key是地点描述description 以及地点 Value是地点Spot之间的映射Map */
	private Map spotDescriptonMap = new HashMap();

	final static int where = 0;// 显示当前在什么地方

	final static int list = 1;// 列出当前位置附近的地点或者物品

	final static int gotos = 2;// 到另一个地点

	final static int look = 3;// 查询某个物品是否在当前地点

	final static int help = 4;// 命令行提示,列出各种命令

	public Visit() {
		location = bd.getSpots()[0];// 当前位置
		mapSpotDescriptioToSpot();
	}

	/**
	 * 实现 spotDescriptio到spot的映射
	 * 
	 * @param sp
	 *            代表地点数组
	 */
	private void mapSpotDescriptioToSpot() {
		Spot[] sp = bd.getSpots();
		int n = sp.length;
		for (int i = 0; i < n; i++) {
			spotDescriptonMap.put(sp[i].description, sp[i]);
		}

	}

	/**
	 * 获取人机交互的命令
	 * 
	 */
	public String getCommand() {
		byte[] b = new byte[20];
		String s = new String();
		try {
			int n = System.in.read(b);// 回车换行也读到了,所以下面要减2
			s = new String(b, 0, n - 2);
			s = s.trim();
		} catch (IOException e) {
			e.printStackTrace();
		} finally {

		}
		return s;
	}

	/**
	 * 处理控制台输入的命令s
	 */
	public boolean processCommand(String s) {
		boolean bl = true;
		if (!(s.compareTo("") == 0)) {
			int n = s.indexOf(' ');
			if (n == -1) {
				if (s.compareToIgnoreCase("where") == 0) {
					processCommand(where);
				} else if (s.compareToIgnoreCase("help") == 0) {
					processCommand(help);
				} else if (s.compareToIgnoreCase("list") == 0) {
					processCommand(list);
				} else
					bl = false;
			} else {
				String s1 = s.substring(0, s.indexOf(' '));
				String s2 = s.substring(s.indexOf(' ') + 1);
				s2=s2.trim();
				if (s1.compareToIgnoreCase("goto") == 0) {
					bl = processCommand(gotos, s2);
				} else if (s1.compareToIgnoreCase("list") == 0) {
					bl = processCommand(list, s2);
				} else if (s1.compareToIgnoreCase("look") == 0) {
					bl = processCommand(look, s2);
				} else
					bl = false;
			}
		}
		return bl;
	}

	/**
	 * 处理各种命令 双参数
	 * 
	 * @param command
	 *            代表命令,例如look,goto,where
	 * @param obj
	 *            代表物品或者地点 比如 电脑,电视,登记表
	 */
	private boolean processCommand(int command, String obj) {
		if (command == gotos) {
			/* 不包含这个地点 */
			if (!spotDescriptonMap.containsKey(obj))
				System.out.println(obj + " is not in the building");
			else {
				Spot sp = (Spot) spotDescriptonMap.get(obj);// 类型转换
				/* 原地 */
				if (sp == location)
					System.out.println("You are at " + location.description
							+ " now.");
				/* 不能直接到这个地点,当前位置与obj不相邻 */
				else if (!location.adjacentList.contains(sp))
					processGotoCommand(sp);
				/* 当前位置移到obj */
				else {
					System.out.println(obj);
					location = sp;
				}
			}
		}
		if (command == list)
			return processListCommand(obj);
		/* 当前地点有没有obj这个物品 */
		else if (command == look) {
			if (!location.goodsList.contains(obj)) {
				System.out.println(obj + " is not at " + location.description);
			} else {
				System.out.println(obj + " is at " + location.description);
			}
		}
		return true;

	}

	/**
	 * 到一个不相邻的地点
	 * 
	 * @param sp
	 *            要去的地点
	 */
	private void processGotoCommand(Spot sp) {
		int n = bd.getSpotNumber();
		float[][] cost = bd.getDistance();/* 相邻地点之间的距离 */
		float[] dist = new float[n];/* 到obj的距离 */
		int[][] path = new int[n][n];/* 到obj的路径 */
		Spot[] spots = bd.getSpots();/* 获取所有地点 */
		int v = location.id;/* 当前地点的编号 */
		int w = sp.id;/* obj的编号 */
		shortestPath(cost, v, n, dist, path);
		float distance = dist[w];
		if (distance == Building.NOTAdjacent) {/* 不可达 */
			System.out.println(sp.description + " cannot be reached from "
					+ location.description);
		} else {
			int length = 0;/* 从v到w中间经历地点个数 */
			while (path[w][length] != -1)
				length++;
			int i = 0;
			for (i = 0; i < length - 1; i++) {
				System.out.print(spots[path[w][i]].description + "->");
			}
			System.out.println(spots[path[w][i]].description);
			location = spots[path[w][i]];
		}

	}

	/**
	 * 
	 * @param obj
	 *            goods spots allspots
	 * @return 参数是否合适
	 */
	private boolean processListCommand(String obj) {
		/* 列出当地物品 */
		if (obj.compareToIgnoreCase("goods") == 0) {
			Iterator itr = location.goodsList.iterator();
			while (itr.hasNext()) {
				Object element = itr.next();
				System.out.print(element + " ");
			}
			System.out.println();
			return true;
		}
		/* 列出附近地点 */
		else if (obj.compareToIgnoreCase("spots") == 0) {
			Iterator itr = location.adjacentList.iterator();
			while (itr.hasNext()) {
				Spot element = (Spot) itr.next();
				System.out.print(element.description + " ");
			}
			System.out.println();
			return true;
		}
		/* 列出大厦内所有地点 */
		else if (obj.compareToIgnoreCase("allspots") == 0) {
			Spot[] spots = bd.getSpots();
			int n = spots.length;
			for (int i = 0; i < n; i++) {
				System.out.print(spots[i].description + " ");
			}
			System.out.println();
			return true;
		} else
			return false;
	}

	/**
	 * 处理各种命令 单参数
	 * 
	 * @param command
	 *            代表命令,例如list,where
	 */
	private void processCommand(int command) {

		switch (command) {
		case where:/* 显示当前位置 */
			System.out.println(location.description);
			break;
		case list: {/* 列出当地物品 */
			Iterator itr = location.goodsList.iterator();
			while (itr.hasNext()) {
				Object element = itr.next();
				System.out.print(element + " ");
			}
			System.out.println();
			break;
		}
		case help: {/* 显示帮助命令 */
			processHelpCommand();
			break;
		}
		default:
			break;
		}

	}

	/**
	 * 处理help命令
	 * 
	 */
	private void processHelpCommand() {
		System.out.println("where 显示当前在什么地方");
		System.out.println("list 列出当前位置的物品");
		System.out.println("list allspots 列出大厦内所有地点");
		System.out.println("list spots 列出当前位置附近的地点");
		System.out.println("list goods 列出当前位置的物品");
		System.out.println("goto someplace 到另一个地点");
		System.out.println("look somegoods 查询某个物品是否在当前地点");
		System.out.println("help 命令行帮助");
		System.out.println("exit 退出命令行");
	}

	/**
	 * 单源最短路径的Dijstra算法
	 * 
	 * @param v
	 *            源
	 * @param cost
	 *            权值
	 * @param n
	 *            结点个数
	 * @param dist
	 *            v到各顶点的距离
	 * @param path
	 *            路径
	 */
	static void shortestPath(float[][] cost, int v, int n, float[] dist,
			int[][] path) {
		int i, w, u, count;
		int[] pos = new int[n];
		int[] s = new int[n];
		for (i = 0; i < n; i++) {
			s[i] = 0;
			dist[i] = cost[v][i];
			path[i][0] = v;
			for (int j = 1; j < n; j++)
				path[i][j] = -1;/* 标记而已 */
			pos[i] = 0;/* 第i条路径的位置计数器 */
		}
		s[v] = 1;
		count = 1;
		while (count < n) {
			u = minDistance(s, dist);
			s[u] = 1;
			path[u][++pos[u]] = u;/* 先自加后操作 */
			count++;
			/* 更新 dist数组 */
			for (w = 0; w < n; w++) {
				if (s[w] == 0 && cost[u][w] < Float.MAX_VALUE
						&& dist[u] + cost[u][w] < dist[w]) {
					dist[w] = dist[u] + cost[u][w];
					pos[w] = pos[u];/* 拷贝 */
					for (i = 0; i <= pos[u]; i++)
						path[w][i] = path[u][i];
				}
			}
		}
	}

	/**
	 * @return u 利用s和dist在尚未找到最短路径的顶点中确定一个与v最接近的顶点
	 * 
	 */
	static int minDistance(int[] s, float[] dist) {

		float min = Float.MAX_VALUE;
		int n = s.length;
		int u = n;
		for (int i = 0; i < n; i++) {
			if (s[i] == 0 && dist[i] < min) {
				min = dist[i];
				u = i;
			}
		}
		return u;
	}

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -