先来一个题目传送门
写这篇博客为了提醒自己做题过程中所犯错误。
代码语言:Object C
1. 矩阵转置
题目描述:输入一个N*N的矩阵,将其转置后输出。要求:不得使用任何数组(就地逆置)。
分析:循环将上三角的元素和对应位置的元素交换即可,当然也可以在输入的时候就调换位置。
code:
#include<stdio.h>
#include<string.h>
int arr[110][110];
int main(){
//freopen("aa.txt", "r", stdin);
int n, i, j;
while(scanf("%d", &n) == 1){
memset(arr, 0, sizeof arr);
for(i = 0; i<n; i++){
for(j = 0; j<n; j++)
scanf("%d", &arr[i][j]);
}
for(i = 0; i<n; i++){
for(j = i+1; j<n; j++){
int tem = arr[i][j];
arr[i][j] = arr[j][i];
arr[j][i] = tem;
}
}
for(i = 0; i<n; i++){
for(j = 0; j<n; j++){
printf("%d", arr[i][j]);
printf(j != n-1 ? " " : "\n");
}
}
}
return 0;
}
2. 统计单词
题目描述:编一个程序,读入用户输入的,以“.”结尾的一行文字,统计一共有多少个单词,并分别输出每个单词含有多少个字符。 (凡是以一个或多个空格隔开的部分就为一个单词)。
分析:scanf读入能分离空格,因此只要不断输入,并且判断输入的字符串最后一个是不是 . 即可
code:
#include<stdio.h>
#include<string.h>
int main(){
//freopen("aa.txt", "r", stdin);
char ch[1010];
while(~scanf("%s", ch)){
int cnt = 0;
int len = strlen(ch), i;
for(i = 0; i<len; i++){
cnt++;
}
if(ch[len-1] == '.') {
cnt--;
printf("%d\n", cnt);
}
else printf("%d ", cnt);
}
return 0;
}
3. IP地址
题目描述:输入一个ip地址串,判断是否合法。
分析:sscanf能将输入的字符串格式化输出,再check每一位的合法性即可。
code:
#include<stdio.h>
int check(int a){
if(a>=0 && a<=255) return 1;
return 0;
}
int main(){
int a, b, c, d;
char ip[10100];
while(~scanf("%s", ip)){
sscanf(ip, "%d.%d.%d.%d", &a, &b, &c, &d);
if(check(a) && check(b) && check(c) && check(d) && a != 0) printf("Yes!\n");
else printf("No!\n");
}
}
4. 二叉排序树
题目描述:二叉排序树,也称为二叉查找树。可以是一颗空树,也可以是一颗具有如下特性的非空二叉树:
1. 若左子树非空,则左子树上所有节点关键字值均不大于根节点的关键字值;
2. 若右子树非空,则右子树上所有节点关键字值均不小于根节点的关键字值;
3. 左、右子树本身也是一颗二叉排序树。
现在给你N个关键字值各不相同的节点,要求你按顺序插入一个初始为空树的二叉排序树中,每次插入后成功后,求相应的父亲节点的关键字值,如果没有父亲节点,则输出-1。
分析:比较正常的二叉排序树
code:
#include<stdio.h>
#include<stdlib.h>
int pp = -1;
struct Node{
int data;
struct Node* lchild, *rchild;
};
struct Node * insert(struct Node* root, int num, int p){
if(root == NULL){
root = (struct Node*)malloc(sizeof(struct Node));
root->data = num;
root->lchild = NULL;
root->rchild = NULL;
pp = p;
return root;
}
if(root->data >= num) root->lchild = insert(root->lchild, num, root->data);
else root->rchild = insert(root->rchild, num, root->data);
return root;
}
int main(){
int n, num, i;
while(~scanf("%d", &n)){
struct Node* root = NULL;
for(i = 0; i<n; i++){
scanf("%d", &num);
root = insert(root, num, -1);
printf("%d\n", pp);
}
}
return 0;
}
还有一种结构体定义的方法,
typedef struct Node{
int data;
struct Node *next;
}Node, *LinkNode;
5. 字符串连接
题目描述: 不借用任何字符串库函数实现无冗余地接受两个字符串,然后把它们无冗余的连接起来。
分析:直接输出
code:
#include<stdio.h>
int main(){
char str1[110], str2[110];
while(~scanf("%s %s", str1, str2)){
printf("%s%s\n", str1, str2);
}
return 0;
}
6. a+b
题目描述:实现一个加法器,使其能够输出a+b的值。
分析:模拟大数加法,最后输出的时候直接输出字符数组会报错,改用按位输出。
code:
#include<stdio.h>
#include<string.h>
void reverse(char a[], int len){
int i;
for(i = 0; i<len/2; i++){
char tem = a[i];
a[i] = a[len-i-1];
a[len-i-1] = tem;
}
}
int main(){
//freopen("aa.txt", "r", stdin);
char a[1010], b[1010], res[1010];
int lena, lenb, i, c, j;
while(~scanf("%s%s", a, b)){
lena = strlen(a), lenb = strlen(b), c = 0;
reverse(a, lena);
reverse(b, lenb);
for(i = 0; i<lena && i<lenb; i++){
int tem = a[i]+b[i]+c-'0'-'0';
c = tem/10;
tem -= c*10;
res[i] = tem+'0';
}
while(i < lena){
int tem = a[i]+c-'0';
c = tem/10;
tem -= c*10;
res[i++] = tem+'0';
}
while(i < lenb){
int tem = b[i]+c-'0';
c = tem/10;
tem -= c*10;
res[i++] = tem+'0';
}
if(c != 0) res[i++] = c + '0';
reverse(res, i);
for(j = 0; j<i; ++j)
printf("%c", res[j]);
printf("\n");
}
return 0;
}
7. 排序
题目描述:对输入的n个数进行排序并输出。
分析:手写快排, 当然也可以直接调用qsort
code:
#include<stdio.h>
int partition(int arr[], int left, int right){
int tem = arr[left], i = left, j = right;
while(i < j){
while(i < j && tem <= arr[j]) j--;
while(i <