一、杨氏矩阵
正常解法
解法:杨氏矩阵其实也是二维数组,通过对比右上角或者左下角的数据。一次消除一行或者一列。
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
/*
杨氏矩阵解法
*/
int find_num(int arr[3][3], int r, int c, int k) {
//找到二维数组的右上角的数据,来对比
int x = 0;
int y = c - 1;
//如果条件不成立,表示x或者y超出二维数组的范围了
while (x < r && y >= 0) {
//一次消除一行
if (arr[x][y] < k) {
x++;
}
//一次消除一列
else if (arr[x][y] > k) {
y--;
}
else {
printf("%d %d\n", x, y);
return 1;
}
}
return 0;
}
int main() {
int arr[3][3] = { 1,2,3,4,5,6,7,8,9 };
int k = 7;
int ret = find_num(arr, 3, 3, k);
if (ret == 1) {
printf("找到了\n");
}
else {
printf("没找到\n");
}
return 0;
}
采用指针来操作
可以记录指针走到哪里,那里就是数组元素下标。
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
int find_num(int arr[3][3], int* px, int* py, int k) {
int x = 0;
int y = *py - 1;
while (x < *px && y >= 0) {
if (arr[x][y] < k) {
x++;
}
else if (arr[x][y] > k) {
y--;
}
else {
*px = x;
*py = y;
return 1;
}
}
return 0;
}
int main() {
int arr[3][3] = { 1,2,3,4,5,6,7,8,9 };
int k = 87;
int x = 3;
int y = 3;
int ret = find_num(arr, &x, &y, k);
if (ret == 1) {
printf("找到了\n");
printf("下标是:%d %d\n", x, y);
}
else {
printf("没找到\n");
}
return 0;
}
二、左旋字符串。
先取出第一个元素
解法:先把第一个元素取出,然后后面的元素依次往前移动一位,最后把第一个元素放在最后的位置上。
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
#include <string.h>
void string_left_rotate(char* str, int k) {
int i = 0;
int n = strlen(str);
for (i = 0; i < k; i++) {
//每次左旋转一个字符
//先把第一个字符取出来
char tmp = *str;
//其余字符依次往前移动
int j = 0;
for (j = 0; j < n - 1; j++) {
*(str + j) = *(str + j + 1);
}
//把第一个字符放在最后的位置
*(str + n - 1) = tmp;
}
}
int main() {
char arr[] = "ABCDEF";
int k = 2;
string_left_rotate(arr, k);
printf("%s\n", arr);
return 0;
}
通过三次逆序解决
先把要左旋转的字符串逆序,然后把不需要旋转的字符串逆序,最后把整体字符串逆序。
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
#include <assert.h>
//逆序字符串,把第一个和最后一个字符串交换
//然后把前后指针向中间移动
void reverse(char* left, char* right) {
assert(left);
assert(right);
while (left < right) {
char tmp = *left;
*left = *right;
*right = tmp;
left++;
right--;
}
}
//定位要移动字符串,不移动字符串,和整体字符串的位置
void string_left_rotate(char* str, int k) {
assert(str);
int n = strlen(str);
reverse(str, str + k - 1);//左
reverse(str + k, str + n - 1);//右
reverse(str, str + n - 1);//整体
}
int main() {
char arr[] = "ABCDEFG";
int k = 4;
string_left_rotate(arr, k);
printf("%s\n", arr);
return 0;
}
三、判断字符串是否是旋转后的字符串
把字符串旋转后和要判断的字符串对比
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
//旋转字符串,是先取出第一个元素的方法
int is_string_rotate(char* str1, char* str2) {
int i = 0;
int n = strlen(str1);
for (i = 0; i < n; i++) {
char tmp = *str1;
int j = 0;
for (j = 0; j < n - 1; j++) {
*(str1 + j) = *(str1 + j + 1);
}
*(str1 + n - 1) = tmp;
if (strcmp(str1, str2) == 0) {
return 1;
}
}
return 0;
}
int main() {
char arr1[] = "AABCD";
char arr2[] = "BCDAA";
int ret = is_string_rotate(arr1, arr2);
if (ret == 1) {
printf("yes\n");
}
else {
printf("no\n");
}
return 0;
}
使用库函数解决
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
#include <string.h>
int is_string_rotate(char* str1, char* str2) {
//判断两个字符串是否相等,不等就不是旋转后的字符串
if (strlen(str1) != strlen(str2)) {
return 0;
}
//把str1字符串,拼接到str1字符串后面
int len = strlen(str1);
strncat(str1, str1, len);
//对比,旋转后的字符串是否是拼接后的str1字符串的子串。
char* ret = strstr(str1, str2);
//strstr返回值不是NULL,就是子串,就是旋转后的字符串。
return ret != NULL;
}
int main() {
char arr1[20] = "AABCD";
char arr2[] = "BCDAA";
int ret = is_string_rotate(arr1, arr2);
if (ret == 1) {
printf("yes\n");
}
else {
printf("no\n");
}
return 0;
}