简体   繁体   English

如何使用大阵列大小?

[英]How to use large array size?

I was trying this problem on spoj. 我在spoj上尝试这个问题。 www.spoj.com/problems/RRANGE.It requires segment tree.But the problem is with the size of array.Here (1 <= N <= 1,000,000,000).Any way to work around this problem? 它需要段树,但问题在于数组的大小,这里(1 <= N <= 1,000,000,000)。有什么方法可以解决此问题? Here is my implementation(gives correct answer for nearly N<1000000) 这是我的实现(给出将近N <1000000的正确答案)

#include <stdio.h>
#include <math.h>
#include<iostream>
#include<string.h>
using namespace std;
//segment tree
long long a[1000000];

long long Mid(long long s,long long e)
{
    return s+(e-s)/2;
}
long long Sum1(long long *st,long long ss,long long se,long long qs,long long qe,long long index)
{
    if (qs<=ss&&qe>=se)
        return st[index];
    if (se<qs||ss>qe)
        return 0;
    long long mid=Mid(ss, se);
    return Sum1(st,ss,mid,qs,qe,2*index+1) +Sum1(st,mid+1,se,qs,qe,2*index+2);
}
void update1(long long *st,long long ss,long long se,long long i,long long diff,long long index)
{
    if (i<ss||i>se)
        return;
    st[index]=st[index]+diff;
    if (se!=ss)
    {
        long long mid = Mid(ss,se);
        update1(st,ss,mid,i,diff,2*index+1);
        update1(st,mid+1,se,i,diff,2*index+2);
    }
}
void update(long long arr[],long long *st,long long n,long long i,long long new_val)
{
    if (i<0||i>n-1)
    return;
    long long diff = new_val - arr[i];
    arr[i] = new_val;
    update1(st,0,n-1,i,diff,0);
}
long long Sum(long long *st,long long n,long long qs,long long qe)
{
    if (qs<0||qe>n-1||qs>qe)
    return -1;
    return Sum1(st,0,n-1,qs,qe,0);
}

long long segtree(long long arr[],long long ss,long long se,long long *st,long long si)
{

    if (ss==se)
    {
        st[si]=arr[ss];
        return arr[ss];
    }


    long long mid=Mid(ss, se);
    st[si]=segtree(arr,ss,mid,st,si*2+1)+segtree(arr,mid+1,se,st,si*2+2);
    return st[si];
}

long long *segt(long long arr[],long long n)
{
    long long x = (long long)(ceil(log2(n)));
    long long max_size = 2*(long long)pow(2, x) - 1;
    long long *st = new long long[max_size];
    segtree(arr,0,n-1,st,0);
    return st;
}
int main()
{
    //memset(a,0,sizeof(a));
    long long n,u,v;
    cin>>n>>u>>v;
    for(long long i=0;i<n;i++)
    a[i]=0;
    long long *st=segt(a,n);


    while(u--)
    {
        long long i,j;
        cin>>i>>j;
        long long z=1;
        for(long long p=i-1;p<j;p++)
        {
        update(a,st,n,p,a[p]+z);
        z++;
        }
    //for(int m=0;m<n;m++)
    //cout<<a[m]<<endl;

    }
    while(v--)
    {
        long long i,j;
        cin>>i>>j;
        cout<<Sum(st,n,i-1,j-1)<<endl;
    }
    return 0;
}

In C or C++ local objects are generally or usually allocated on the stack. 在C或C ++中,本地对象通常或通常分配在堆栈上。 Since you are allocating a very large array on the stack. 由于您要在堆栈上分配一个非常大的数组。 So you have a chance of getting a stack overflow . 这样您就有机会使堆栈溢出 I would recommend you to use std::vector<int> and resize it to 1000000 elements. 我建议您使用std::vector<int>并将其大小调整为1000000个元素。

Whatever solution you try you will need more than 8 GB of ram to solve the problem using this algorithm. 无论您尝试哪种解决方案,都将需要8 GB以上的ram才能使用此算法解决问题。 Memory limit on spoj is way less. spoj的内存限制要少得多。 Think of an alternative solution that requires less memory. 考虑一种需要较少内存的替代解决方案。

You can try using a binary indexed tree instead of a segment tree -> here is a nive tutorial. 您可以尝试使用binary indexed tree而不是segment tree -> 是一个简单的教程。

A BIT takes O(n) memory, compared to a segment tree's O(2^(logN+2)), and it can serve the same purpose. 与段树的O(2 ^(logN + 2))相比,BIT占用O(n)内存,并且可以达到相同的目的。

Hope this helps... 希望这可以帮助...

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM