#include <stdio.h>
#include <string>
#include <cstring>
#include <stdlib.h>
#include <math.h>
#include <algorithm>
#include <vector>
#include <set>
#include <map>
#include <queue>
#include <list>
#include <iterator>
#pragma warning(disable:4996)
 
typedef long long ll;
#define MIN(a, b) ((a)>(b)? (b): (a))
#define MAX(a, b) ((a)<(b)? (b): (a))
#define LINF 9223300000000000000
#define INF 2140000000
#define MOD 1000000007
using namespace std;

long n;
vector<long> a;

struct MyPair
{
    long   first;
    list<pair<long,long> >::iterator  second;

    MyPair( long in_first,  list<pair<long,long> >::iterator in_second )
    {
        first = in_first;
        second = in_second;
    }
    bool operator<(const MyPair& rhs) const
    {
        return first < rhs.first;
    };
};

bool check( long m )
{
    list<pair<long,long> > zz;     // (length,num)
    long i;
    for(i=0; i<n; i++) {
        if(!zz.empty() && zz.back().first==a[i]) {
            zz.back().second ++;
        }
        else {
            zz.push_back( make_pair(a[i], 1) );
        }
    }

    vector<MyPair> vec;
    vec.reserve( zz.size());
    {        
        auto cit=zz.begin();
        for(; cit!=zz.end(); ++cit) {
            vec.push_back( MyPair(cit->first, cit) );
        }
        sort(vec.rbegin(), vec.rend());
    }

    for(i=0; i<(long)vec.size(); i++) {
        auto curr = vec[i].second;

        auto prev = curr;
        if(curr!=zz.begin()) {
            prev --;        
        }

        auto next = curr;
        next ++;

        // check if curr can be merged to prev or next
        if(curr!=zz.begin() && prev->first==curr->first) {
            // merge curr to prev
        }
        else if(next!=zz.end() && next->first==curr->first) {
            // merge curr to next
        }
        else {
            // modify curr
            if(curr==zz.begin() && next==zz.end() ) {
                long tmp0 = curr->second;
                if(m==1) {
                    if(tmp0>1) return false;
                    else       return true;
                }
                else {
                    tmp0--;
                    long k;
                    for(k=0; k<(curr->first); k++) {
                        tmp0 = tmp0/m;
                        if(tmp0==1) break;
                    }
                    if(tmp0>0) return false;
                    else       return true;
                }
            }
            else if(curr!=zz.begin() && (next==zz.end() || prev->first >= next->first) ) {
                long tmp0 = curr->second;
                if(m==1) {
                    if(tmp0>1) return false;
                    curr->second = 0;
                    curr->first = prev->first;
                }
                else {
                    tmp0--;
                    long k;
                    for(k=0; k<(curr->first-prev->first); k++) {
                        tmp0 = tmp0/m;
                        if(tmp0==0) break;
                    }
                    curr->second = tmp0;
                    curr->first = prev->first;
                }
            }
            else {
                long tmp0 = curr->second;
                if(m==1) {
                    if(tmp0>1) return false;
                    curr->second = (curr==zz.begin()? 1: 0);
                    curr->first = next->first;
                }
                else {
                    tmp0--;
                    long k;
                    for(k=0; k<(curr->first-next->first); k++) {
                        tmp0 = tmp0/m;
                        if(tmp0==0) break;
                    }
                    curr->second = tmp0+1;
                    curr->first = next->first;
                }
            }
        }

        if(curr!=zz.begin() && prev->first==curr->first) {
            // merge curr to prev
            prev->second += curr->second;
            if(prev->first==1 && prev->second>m) return false;
            zz.erase(curr);
            continue;
        }
        else if(next!=zz.end() && next->first==curr->first) {
            // merge curr to next
            next->second += curr->second;
            if(next->first==1 && next->second>m) return false;
            zz.erase(curr);
            continue;
        }
    }

    return true;
}

int main(int argc, char* argv[])
{
    scanf("%ld", &n);

    a.resize(n);
    long i;
    for(i=0; i<n; i++) {
        scanf("%ld", &a[i]);
    }

    long l=0, r=n;
    while(r-l>1) {
        long m=(l+r)/2;
        if( check(m) ) {
            r = m;
        }
        else {
            l = m;
        }
    }
    printf("%ld\n", r);

    return 0;
}



Measured memory_bytes: 14356