2018年春招网易笔试题-数对问题o(n-k)解法

题目描述

牛牛以前在老师那里得到过一个整数对(x,y),牛牛忘记他们具体是多少了,只记得老师说过,x和y均不大于n,且x%y不小于k,牛牛希望你能帮他计算一共有多少种可能的整数对。

输入描述:两个整数n,k。其中1<=n<=10^5, 0<=k<=n-1

输出描述:输出可能的正整数对的个数。


思路:

暴力破解所有整数对,需要o(n^2),会超时。

其实是个数学问题:

1. y必然大于k,x必然不小于k,才可能产生不小于k的余数;

2.x一定可以表示为:x = i*y + k'  (0<x<= n) ,其中i可以理解为倍数,(0<= i < n/y,共n/y个可能的i),k'为(k,y-1)之间的任意数,共(y-k)种;所以一共有(n/y)*(y-k)种情况。

3.当i取到n/y时,x = i*y + k'可能大于n,所以要计算这里面可能出现的,不大于n的情况,即max(0, n- ( i*y+ k) ));

针对以上三个问题,可以大大简化计算的复杂度。

代码:

import java.util.*;
public class Main {
    public static void main(String args[]) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        int k = scanner.nextInt();
        int y = 1;
        int factor = 1;
        long sumCnt = 0;
        if(k == 0) {
            System.out.println(n*n);
        }
        for(y = k + 1; y <= n; y++) {
            factor = n / y;
            sumCnt += factor * (y - k);
            sumCnt +=  Math.max(0, n - (factor * y + k) + 1);
        }
        System.out.println(sumCnt);
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值