函数题48道
练习5-1 求m到n之和
int sum( int m, int n ){
int temp=0;
for(int i=m;i<=n;i++){
temp +=i;
}
return temp;
}
练习5-2 找两个数中最大者
int max( int a, int b ){
return a>b?a:b;
}
练习5-3 字符金字塔
void CharPyramid( int n, char ch){
for(int i=0;i<n;i++){
for(int j=0;j<n-1-i;j++){
printf(" ");
}
for(int j=0;j<=i;j++){
printf("%c ",ch);
}
printf("\n");
}
}
习题5-1 符号函数
int sign( int x ){
if(x>0){
return 1;
}else{
return x==0?0:-1;
}
}
习题5-2 使用函数求奇数和
int even( int n ){
return n%2==0?1:0;
}
int OddSum( int List[], int N ){
int sum=0;
for(int i=0;i<N;i++){
if(!even(List[i]))sum+=List[i];
}
return sum;
}
习题5-3 使用函数计算两点间的距离
double dist( double x1, double y1, double x2, double y2 ){
return sqrt(pow((x1-x2),2)+pow((y1-y2),2));
}
习题5-4 使用函数求素数和
int prime( int p ){
if(p<2)return 0;
for(int i=2;i*i<=p;i++){
if(p%i==0){
return 0;
}
}
return 1;
}
int PrimeSum( int m, int n ){
int sum=0;
for(int i=m;i<=n;i++){
sum+=prime(i)==1?i:0;
}
return sum;
}
习题5-5 使用函数统计指定数字的个数
int CountDigit( int number, int digit ){
number=number<0?-number:number;
int cnt=0;
if(number==digit)return 1;
while(number!=0){
if(number%10==digit){
cnt++;
}
number /=10;
}
return cnt;
}
习题5-6 使用函数输出水仙花数
#include <math.h>
int narcissistic( int number ){
int cnt=0;
int temp1=number,temp2=number;
while(temp1!=0){//统计位数
cnt++;
temp1 /=10;
}
int sum=0;
while(temp2!=0){//计算每个位上的数字的N次幂之和
sum +=pow(temp2%10,cnt);
temp2 /=10;
}
return number==sum?1:0;
}
void PrintN( int m, int n ){
for(int i=m+1;i<n;i++){
if(narcissistic(i))printf("%d\n",i);
}
}
习题5-7 使用函数求余弦函数的近似值
double funcos( double e, double x ){
double temp=1.0,res=1.0;
for(int i=2;;i+=2){
temp *=(-1)*x*x/(i*(i-1));
res +=temp;
if(fabs(temp)<e)return res;//退出条件
}
}
习题5-8 空心的数字金字塔
#include <string.h>
void hollowPyramid( int n ){
if(n==1){//注意!
printf("1\n");
return;
}
char arr[20]={0};//定义一行字符串
//打印特殊第一行
memset(arr,0,sizeof(arr));
//前空格
int pos;
for(int j=0;j<n-1;j++){
arr[j]=' ';
pos=j;
}
//左数字
arr[pos+1]='0'+1;
printf("%s\n",arr);
//打印2~n-1行
for(int i=2;i<n;i++){
memset(arr,0,sizeof(arr));
//前空格
int pos;
for(int j=0;j<n-i;j++){
arr[j]=' ';
pos=j;
}
//左数字
arr[pos+1]='0'+i;
//中间空格
int pos2=0;
for(int j=0;j<i*2-3;j++){
arr[pos+2+j]=' ';
pos2=pos+2+j;
}
//右数字
arr[pos2+1]='0'+i;
//打印一行字符串
printf("%s\n",arr);
}
//打印特殊最后一行
memset(arr,0,sizeof(arr));
for(int i=0;i<n*2-1;i++){
arr[i]='0'+n;
}
printf("%s\n",arr);
}
习题6-1 分类统计字符个数
#include <ctype.h>
void StringCount( char s[] ){
int cntl=0,cntb=0,cntd=0,cnto=0;
for(int i=0;s[i]!='\0';i++){
if(isalpha(s[i])){
cntl++;
}else if(isspace(s[i])){
cntb++;
}else if(isdigit(s[i])){
cntd++;
}else{
cnto++;
}
}
printf("letter = %d, blank = %d, digit = %d, other = %d",cntl,cntb,cntd,cnto);
}
习题6-2 使用函数求特殊a串数列和
int fn( int a, int n ){
int res=a;
if(n==1)return res;
for(int i=0;i<n-1;i++){
a *=10;
res += a;
}
return res;
}
int SumA( int a, int n ){
int sum=0;
for(int i=1;i<=n;i++){
sum +=fn(a,i);
}
return sum;
}
习题6-3 使用函数输出指定范围内的完数
int factorsum( int number ){
int sum=0;
for(int i=1;i<number;i++){
if(number%i==0)sum +=i;
}
return sum;
}
void PrintPN( int m, int n ){
int flag=0;
for(int i=m;i<=n;i++){
if(factorsum(i) == i){
flag=1;
printf("%d = 1",i);
for(int j=2;j<i;j++){
if(i%j==0){
printf(" + %d",j);
}
}
printf("\n");
}
}
if(!flag)printf("No perfect number");
}
习题6-4 使用函数输出指定范围内的Fibonacci数
int dp[10000]={0};
int fib( int n ){//用递归超时,故改用动态规划记录子状态
dp[0]=0;
dp[1]=1;
for(int i=2;i<10000;i++){
dp[i]=dp[i-1]+dp[i-2];
}
return dp[n];
}
void PrintFN( int m, int n) {
int flag=0;
int first=1;
for(int i=1;;i++){
if(fib(i)>n)break;
if(fib(i)>=m){
if(first){//第一个输出前无空格
printf("%d",fib(i));
first=0;
}else{
printf(" %d",fib(i));
}
flag=1;//有斐波那契数
}
}
if(!flag)printf("No Fibonacci number");
}
习题6-5 使用函数验证哥德巴赫猜想
int prime( int p ){
if(p<2)return 0;
for(int i=2;i*i<=p;i++){
if(p%i==0){
return 0;
}
}
return 1;
}
void Goldbach( int n ){
for(int i=2;n-i>0;i++){
if(prime(i)&&prime(n-i)){
printf("%d=%d+%d",n,i,n-i);
break;
}
}
}
习题6-6 使用函数输出一个整数的逆序数
int reverse( int number ){
if(number==0)return 0;
//负数
int flag=0;
if(number<0){
flag=1;
number = -number;
}
//除去末尾所有0
while(number%10==0){
number /=10;
}
//取余保存每位数
int pos[100];
int cnt=0;
while(number!=0){
pos[cnt++]=number%10;
number /=10;
}
//拼凑逆序数
int res=0;
int temp=0;
for(int i=0;i<cnt;i++){
temp =pos[i];
res = res*10+temp;
}
return flag==1?-res:res;
}
练习8-2 计算两数的和与差
void sum_diff( float op1, float op2, float *psum, float *pdiff ){
*psum=op1+op2;
*pdiff=op1-op2;
}
练习8-8 移动字母
void Shift( char s[] ){
//保存s前三个字符
char temp[3];
int i;
for(i=0;i<3;i++){
temp[i]=s[i];
}
//后面字符依次前移3位
int pos;
for(pos=0;s[pos]!='\0';pos++){
s[pos]=s[pos+3];
}
//s后面添加temp
while(i!=0){
s[pos-i]=temp[3-i];
i--;
}
}
习题8-1 拆分实数的整数与小数部分
void splitfloat( float x, int *intpart, float *fracpart ){
*intpart=(int)x;
*fracpart=x-*intpart;
}
习题8-2 在数组中查找指定元素
int search( int list[], int n, int x ){
for(int i=0;i<n;i++){
if(x==list[i])return i;
}
return -1;
}
习题8-3 数组循环右移
void ArrayShift( int a[], int n, int m ){
//特殊:右移n的倍数,不变
if(m%n==0)return;
m=m%n;
//temp保存后m个数a[n-m]~a[n-1]
int temp[m];
for(int i=0;i<m;i++){
temp[i]=a[i+n-m];
}
//a[n-m-1]~a[0]依次往右移m个位置
for(int i=0;i<n-m;i++ ){
a[n-1-i]=a[n-m-1-i];
}
//把temp元素放到a前面m个位置
for(int i=0;i<m;i++){
a[i]=temp[i];
}
}
习题8-4 报数
(约瑟夫问题,c语言没有现成的队列结构,把out[]逻辑上当成循环数组,标记退出时间以及是否退出状态。)
void CountOff(int n, int m, int out[]) {
// 初始化:所有人都在圈子里
for (int i = 0; i < n; i++) {
out[i] = 0;
}
int say = 0; // 当前报的数
int pos = 1; //第几个退出的人的编号(1~n)
int i = 0; // 数组下标
while (pos <= n) {//已退出n-1个人时结束
// 如果这个人还在圈子里
if (out[i] == 0) {
say++; // 报数
if (say == m) {
// 报到m了,退出
out[i] = pos++;//第pos个退出的
say = 0; // 重置报数
}
}
// 注意!移动到下一个人 (到了out队尾要回到队首)
i = (i + 1) % n;
}
}
习题8-5 使用函数实现字符串部分复制
void strmcpy( char *t, int m, char *s ){
if(m>20)s="";
int i;
for(i=0;t[i]!='\0';i++){
s[i]=t[m-1+i];
}
s[i]='\0';//注意字符数组结尾符,不然会有脏数据
}
习题8-6 删除字符
void delchar( char *str, char c ){
int p;
for(int i=0;str[i]!='\0';i++){
while(str[i]==c){//一旦相同,就用后面全部字符覆盖
p=i;
while(str[p]!='\0'){
str[p]=str[p+1];
p++;
}
}
}
}
浙大版《C语言程序设计第4版》 文章被收录于专栏
PTA链接:https://pintia.cn/problem-sets/1298273728383766528/exam/problems/type/6 (ps:没有书的,账号可以咸🐟️go)
查看15道真题和解析