Chapter 1 Arrays and Strings

这篇博客探讨了几个字符串处理问题,包括如何判断字符串中是否有重复字母,比较两个字符串是否为异构词,如何替换空格为%20,以及如何压缩字符串。此外,还提到了矩阵旋转90度的方法,强调了在遍历矩阵时的计算逻辑和元素位置关系。
摘要由CSDN通过智能技术生成

1. 在string中是否含有重复字母

public static boolean hasUniqueChar(String string) {
	// Total 256 characters in ASCII
	if (string.length() > 256) {
		return false;
	}
	boolean[] count = new boolean[256];
	for (int i = 0; i < string.length(); i++) {
		// If visited before
		if (count[(int) string.charAt(i)]) {
			return false;
		}
		// Initialize
		count[(int) string.charAt(i)] = true;
	}
	return true;
}
在ASCII(非Unicode)编码中,共有256个字符。如果string长度超过256,则肯定有重复。

使用一个数组count来表征这个string,数组初始值为false。每个字母对应一个数组里的元素,index是其ASCII码。

该程序将赋值和判断合二为一,先判断再赋值。

如果输入string只含有a到z的字母,则可以用int替代数组。

public static boolean hasUniqueLowerChar(String string) {
	// An int is 32 bits. a to z is 26
	int count = 0;
	// Use 1 bit to represent a character.
	for (int i = 0; i < string.length(); i++) {
		int val = string.charAt(i) - 'a';
		int bit = 1 << val;
		if ((count & bit) > 0) {
			return false;
		}
		count |= bit;
	}
	return true;
}
一个int为32位,而a到z共有26个字母,故可以用1 bit来表示一个字母(如 0000100)。凡是需要一系列标志位的,如果数量少(32 位用int,64位以内用long),可以考虑用bit vector。

使用一个整数count来表征这个string,初始值为0。每个字母对应count里的一位bit,如果有则为1,如果无则为0。

该程序将赋值和判断合二为一,先判断再赋值。


2. 比较两个string是不是异构词

简单的想,只要比较排序后两个string是否equal即可。

public static boolean isPermux(String s, String t) {
	if (s.length() != t.length()) {
		return false;
	}
	char[] sArray = s.toCharArray();
	char[] tArray = t.toCharArray();
	Arrays.sort(sArray);
	Arrays.sort(tArray);
	return Arrays.equals(sArray, tArray);
}
这里用了Arrays的API函数sort和equals。直接用数组的equals等价于==,故不适用。

public static boolean isPermutation(String s, String t) {
	if (s.length() != t.length()) {
		return false;
	}
	int[] count = new int[256];
	for (int i = 0; i < s.length(); i++) {
		count[s.charAt(i)]++;
	}
	for (int i = 0; i < t.length(); i++) {
		if (--count[t.charAt(i)] < 0) {
			return false;
		}
	}
	return true;
}
首先两个string的长度要一致才可能是异构词(“abcd”, "dcab")。

用一个数组count来表示第一个string,数组初始化为0,记录每个字母出现次数。同样假设是ASCII编码。

利用数组count来比较另一个string,只有当两个string的字母计数一致才是变化词。


3. 将空格替换为%20

public static void replaceSpace(char[] string, int length) {
	int spaceCount = 0;
	for (char i : string) {
		if (i == ' ') {
			spaceCount++;
		}
	}
	int newLength = length + 2 * spaceCount;
	int i = length - 1;
	int j = newLength - 1;
	while (i >= 0) {
		if (string[i] != ' ') {
			string[j] = string[i];
		} else {
			string[j--] = '0';
			string[j--] = '2';
			string[j] = '%';
		}
		i--;
		j--;
	}
}
两次遍历法:第一次从头到尾数空格的数量,确定新string长度;第二次从尾到头,填充新string。

4. 压缩string,将字母计数

例如:aabcccccaaa 压缩为a2b1c5a3,abcdefg 压缩后长度没有减小故仍返回abcdefg。

public static String compressString(String string) {
	StringBuffer sb = new StringBuffer();
	char last = string.charAt(0);
	int count = 1;
	for (int i = 1; i < string.length(); i++) {
		if (string.charAt(i) == last) {
			count++;
		} else {
			sb.append(last);
			sb.append(count);
			last = string.charAt(i);
			count = 1;
		}
	}
	sb.append(last);
	sb.append(count);
	if (sb.length() >= string.length()) {
		return string;
	} else {
		return sb.toString();
	}
}
注意要把最后的字母append上,count从1计数。

5. 旋转矩阵90度

例如:[1,2; 3,4] 旋转为 [3,1; 4,2]

public static void rotateImage(int[][] matrix) {
<span style="white-space:pre">	</span>int n = matrix.length;
	for (int row = 0; row < n / 2; row++) {
<span style="white-space:pre">	</span>	// n - row - 1 - row + 1 = n - 2*row 
<span style="white-space:pre">	</span>	for (int col = row; col < n - row - 1; col++) {
	<span style="white-space:pre">	</span>	int temp = matrix[row][col];
		<span style="white-space:pre">	</span>// left to top
<span style="white-space:pre">	</span>		matrix[row][col] = matrix[n - 1 - col][row];
	<span style="white-space:pre">	</span>	// bottom to left
		<span style="white-space:pre">	</span>matrix[n - 1 - col][row] = matrix[n - 1 - row][n - 1 - col];
<span style="white-space:pre">	</span>		// right to bottom
	<span style="white-space:pre">	</span>	matrix[n - 1 - row][n - 1 - col] = matrix[col][n - 1 - row];
		<span style="white-space:pre">	</span>// top to right
<span style="white-space:pre">	</span>		matrix[col][n - 1 - row] = temp;
	<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>}
}
1. 只需要转一半的行。

2. 以对角线上的元素为基础。for循环次数记得用减法来确定。每下一层,列size减2,故size为n - 2*row。起点为row,则条件为 n - 2*row + row - 1。

3. 画矩阵,判断元素位置的关系。

0,00,10,20,3
1,01,11,21,3
2,02,12,22,3
3,03,13,23,3

1,1 = 2,1
2,1 = 2,2
2,2 = 1,2
每一行颜色相同的值相同,颜色不同的和为定值。

矩阵中有0的地方,使其行列均变成0。
public static void setZeroCross(int[][] matrix) {
	boolean[] row = new boolean[matrix.length];
	boolean[] col = new boolean[matrix[0].length];
	for (int i = 0; i < matrix.length; i++) {
		for (int j = 0; j < matrix[0].length; j++) {
			if (matrix[i][j] == 0) {
				row[i] = true;
				col[j] = true;
			}
		}
	}
	// Nullify rows
	for (int i = 0; i < row.length; i++) {
		if (row[i]) {
			for (int j = 0; j < matrix[0].length; j++) {
				matrix[i][j] = 0;
			}
		}
	}
	// Nullify cols
	for (int i = 0; i < col.length; i++) {
		if (col[i]) {
			for (int j = 0; j < matrix.length; j++) {
				matrix[j][i] = 0;
			}
		}
	}
}
利用两个标志位数组分别存放行置零标志和列置零标志,来区分哪些是原矩阵的0,哪些是要变成0。首先遍历,找到0位置,置对应的行列标志位。
然后依次置相应的行列为0。

7. 判断是否是旋转string
例如:waterbottle 和 erbottlewat 。由x = wat,y = erbottle 两段组成。xy 和 yx 两种组合都是 xyxy组合的子string。
public static boolean isRotation(String s1, String s2) {
	if (s1.length() != s2.length()) {
		return false;
	}
	String s1s1 = s1 + s1;
	return isSubstring(s1s1, s2);
}
public static boolean isSubstring(String s, String t) {
	if (s.length() < t.length()) {
		return false;
	}
	int sIndex = 0;
	int tIndex = 0;
	while (sIndex < s.length()) {
		if (s.charAt(sIndex) == t.charAt(tIndex)) {
			tIndex++;
		} else {
			tIndex = 0;
		}
		sIndex++;
		if (tIndex == t.length()) {
			return true;
		}
	}
	return false;
}
将一个string自己复制组合,判断另一个string是不是这个组合string的子string。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值