CF-50E-Square Equation Roots(数论)

本文探讨了一类特殊形式的一元二次方程x² + 2bx + c = 0对于所有可能的b和c值(1 ≤ b ≤ n, 1 ≤ c ≤ m)时的不同实数根的数量问题。通过分析不同b和c值下方程的实根情况,提出两种算法方案:一是计算所有根并去重;二是通过数学规律快速求解。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

E - Square Equation Roots
Time Limit:5000MS     Memory Limit:262144KB     64bit IO Format:%I64d & %I64u

Description

A schoolboy Petya studies square equations. The equations that are included in the school curriculum, usually look simple:

x2 + 2bx + c = 0
where  bc are natural numbers.

Petya noticed that some equations have two real roots, some of them have only one root and some equations don't have real roots at all. Moreover it turned out that several different square equations can have a common root.

Petya is interested in how many different real roots have all the equations of the type described above for all the possible pairs of numbers b and c such that 1 ≤ b ≤ n1 ≤ c ≤ m. Help Petya find that number.

Input

The single line contains two integers n and m. (1 ≤ n, m ≤ 5000000).

Output

Print a single number which is the number of real roots of the described set of equations.

Sample Input

Input
3 3
Output
12
Input
1 2
Output
1

Hint

In the second test from the statement the following equations are analysed:

b = 1c = 1x2 + 2x + 1 = 0; The root is x =  - 1

b = 1c = 2x2 + 2x + 2 = 0; No roots

Overall there's one root

In the second test the following equations are analysed:

b = 1c = 1x2 + 2x + 1 = 0; The root is x =  - 1

b = 1c = 2x2 + 2x + 2 = 0; No roots

b = 1c = 3x2 + 2x + 3 = 0; No roots

b = 2c = 1x2 + 4x + 1 = 0; The roots are 

b = 2c = 2x2 + 4x + 2 = 0; The roots are 

b = 2c = 3x2 + 4x + 3 = 0; The roots are x1 =  - 3, x2 =  - 1

b = 3c = 1x2 + 6x + 1 = 0; The roots are 

b = 3c = 2x2 + 6x + 2 = 0; The roots are 

b = 3c = 3x2 + 6x + 3 = 0; The roots are  Overall there are 13 roots and as the root  - 1 is repeated twice, that means there are 12 different roots.


思路:1:先算出所有的根,包括重根,然后用数组存出现过的整数根,然后去重根。

(我原先有想过这样去重的,一直觉得会超时TLE的,因为for一遍m就需要5*10^6,for里在枚举去重,那也需要sqrt(5*10^6)怎么可能不TLE呢?后来想想最坏复杂复杂度这样算有点不靠谱,但我觉得仍然这种方法应该超时,就没去试,悲剧的啊!要不比赛的时候就A了,才用了230MS啊)

2:比赛的时候感觉上一种超时,所以找规律,而且也确实找到了,b每增加1重根数就多两个可是当c太小时,有的根就构造不出来,这种情况,当时我是想整左右边界来搞定,敲了会代码发现有点蒙,结果就放弃了。这种房方法31MS能过。

#include<iostream>
#include<cstring>
using namespace std;
const int mm=5010000;
bool vis[mm];
long long m,n,pos,num;
int main()
{

  /*for(int i=0;i*i<mm;i++)
  {
    vis[i*i]=i;
  }*/
  while(cin>>m>>n)
  { memset(vis,0,sizeof(vis));
    long long sum=0,z;
    for(pos=n;pos>=0;pos--)
      if(vis[pos])
      break;
    for(long long i=1;i<=m;i++)
    { z=i*i;
      if(z<=n)///计算所有的根包括重复的根
      {
        sum+=z*2;
      }
      else
      {
        sum+=n*2;
      }
      for(long long j=i-1;j>=0;--j)///枚举去除重复的根
      {
        if(i*i-j*j>n)break;///当i*i-j*j>n时,n已经构造不出j了
        if(vis[i-j])--sum;
        else vis[i-j]=1;
        if(vis[i+j])--sum;
        else vis[i+j]=1;
      }
    }
    cout<<sum<<"\n";
  }
}


#include<iostream>
#include<cstring>
using namespace std;
const int mm=5010000;
long long m,n,pos,num;
inline long long  ma(long long a,long long b)
{
  if(a<b)return b;return a;
}
int main()
{
  while(cin>>m>>n)
  {
    long long sum=0,z;
    for(long long i=1;i<=m;i++)
    { z=i*i;
      if(z<=n)///计算所有的根不包括单重复的根
      {
        sum+=z*2-1;
      }
      else
      {
        sum+=n*2;
      }
    }
    int _mi;
    for(long long i=-m-m;i<0;++i)
      {
        _mi=ma(-m-m-i,n/i);
        if(i&1)--_mi;
        _mi=(-_mi)>>1;
        --_mi;
        if(_mi>0)sum-=_mi;
      }
    cout<<sum<<"\n";
  }
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值