#include <iostream>
#include<bits/stdc++.h>
using namespace std;
int Arr[100005];
int seg[400002][2];
int segdp[400002];
int dp[100005];
void build(int id,int l,int r) {
if(l==r) {
        seg[id][0] = seg[id][1]  = Arr[l];
        return;
}
int mid=  (l+r)/2;
build(id*2,l,mid);
build(id*2+1,mid+1,r);
seg[id][0] = min(seg[id*2][0],seg[id*2+1][0]);
seg[id][1] = max(seg[id*2][1],seg[id*2+1][1]);
}
int qu(int id,int l,int r,int x,int y,int s) {
if(l > y || r <x) return (s) ? INT_MAX : -INT_MAX;
if(l >=x && r<=y)  return (s) ? seg[id][0] : seg[id][1];
int mid = (l+r)/2;
return (s) ? min(qu(id*2,l,mid,x,y,s),qu(id*2+1,mid+1,r,x,y,s)) : max(qu(id*2,l,mid,x,y,s),qu(id*2+1,mid+1,r,x,y,s)) ;
}
void upd(int id,int l,int r,int x,int v) {
if(x > r || x < l) return ;
if(x>=l && x<=r) {
    if(l==r) {
        segdp[id] = v;
        return;
    }
}
upd(id*2,l,(l+r)/2,x,v);
upd(id*2+1,(l+r)/2+1,r,x,v);
segdp[id] = min(segdp[id*2],segdp[id*2+1]);
}
int q(int id,int l,int r,int x,int y) {
if(l > y || r <x) return INT_MAX;
if(l>=x && r<=y) return segdp[id];
int mid = (l+r)/2;
return min(q(id*2,l,mid,x,y),q(id*2+1,mid+1,r,x,y));
}
int main()
{
    ios_base::sync_with_stdio(false);
    int n,s,le;
    cin >> n >> s >> le;
    for(int i =0;i<n;i++) cin >> Arr[i];
    build(1,0,n-1);
    for(int i =le-1;i<n;i++) {
            if(i<2*le-1) dp[i] = (qu(1,0,n-1,0,i,0) - qu(1,0,n-1,0,i,1) <= s) ? 1 : INT_MAX;
            else dp[i] = (qu(1,0,n-1,0,i,0) - qu(1,0,n-1,0,i,1) <= s) ? 1 : 0;
            upd(1,0,n-1,i,dp[i]);
    }
    for(int i =2*le-1;i<n;i++) {
        int mid;
        int l =le;
        int diff=-INT_MAX;
        int r = i-le+1;
        for(int j =0;j<20;j++){
            mid = (l+r)/2;
            diff = qu(1,0,n-1,mid,i,0) - qu(1,0,n-1,mid,i,1);
            if(diff > s) l = mid+1;
            else r = mid;
        }
        if(diff > s && !dp[i]) dp[i] = INT_MAX;
        else {
                int z =q(1,0,n-1,mid-1,i-le);
                if(z==INT_MAX) dp[i] = z;
                else {
                    if(!dp[i]) dp[i] = z+1;
                    else dp[i] = min(dp[i],z+1);
                }
        }
        upd(1,0,n-1,i,dp[i]);
    }
    if(!dp[n-1] || dp[n-1] == INT_MAX) cout << -1;
    else cout << dp[n-1];
    return 0;
}


#include <iostream>
#include<bits/stdc++.h>
using namespace std;
int Arr[100005];
int seg[400002][2];
int segdp[400002];
int dp[100005];
void build(int id,int l,int r) {
if(l==r) {
        seg[id][0] = seg[id][1]  = Arr[l];
        return;
}
int mid=  (l+r)/2;
build(id*2,l,mid);
build(id*2+1,mid+1,r);
seg[id][0] = min(seg[id*2][0],seg[id*2+1][0]);
seg[id][1] = max(seg[id*2][1],seg[id*2+1][1]);
}
pair<int,int> qu(int id,int l,int r,int x,int y) {
if(l > y || r <x) return {INT_MAX,-INT_MAX};
if(l >=x && r<=y)  return  {seg[id][0],seg[id][1]};
pair<int,int> a = qu(id*2,l,(l+r)/2,x,y);
pair<int,int> b = qu(id*2+1,(l+r)/2+1,r,x,y);
return {min(a.first,b.first),max(a.second,b.second)};
}
void upd(int id,int l,int r,int x,int v) {
if(x > r || x < l) return ;
if(x>=l && x<=r) {
    if(l==r) {
        segdp[id] = v;
        return;
    }
}
upd(id*2,l,(l+r)/2,x,v);
upd(id*2+1,(l+r)/2+1,r,x,v);
segdp[id] = min(segdp[id*2],segdp[id*2+1]);
}
int q(int id,int l,int r,int x,int y) {
if(l > y || r <x) return INT_MAX;
if(l>=x && r<=y) return segdp[id];
int mid = (l+r)/2;
return min(q(id*2,l,mid,x,y),q(id*2+1,mid+1,r,x,y));
}
int main()
{
    ios_base::sync_with_stdio(false);
    int n,s,le;
    cin >> n >> s >> le;
    for(int i =0;i<n;i++) cin >> Arr[i];
    build(1,0,n-1);
    for(int i =le-1;i<n;i++) {
            pair<int,int> ans = qu(1,0,n-1,0,i);
            int dff = ans.second - ans.first;
            if(i<2*le-1) dp[i] = (dff <= s) ? 1 : INT_MAX;
            else dp[i] = (dff <= s) ? 1 : 0;
            upd(1,0,n-1,i,dp[i]);
    }
    for(int i =2*le-1;i<n;i++) {
        int mid;
        int l =le;
        int diff=-INT_MAX;
        int r = i-le+1;
        for(int j =0;j<20;j++){
            mid = (l+r)/2;
            pair<int,int> ans = qu(1,0,n-1,mid,i);
            diff = ans.second-ans.first;
            if(diff > s) l = mid+1;
            else r = mid;
        }
        if(diff > s && !dp[i]) dp[i] = INT_MAX;
        else {
                int z =q(1,0,n-1,mid-1,i-le);
                if(z==INT_MAX) dp[i] = z;
                else {
                    if(!dp[i]) dp[i] = z+1;
                    else dp[i] = min(dp[i],z+1);
                }
        }
        upd(1,0,n-1,i,dp[i]);
    }
    if(!dp[n-1] || dp[n-1] == INT_MAX) cout << -1;
    else cout << dp[n-1];
    return 0;
}


// hloya template v23

// ░░░░░░░▄▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▄░░░░░░
// ░░░░░░█░░▄▀▀▀▀▀▀▀▀▀▀▀▀▀▄░░█░░░░░
// ░░░░░░█░█░▀░░░░░▀░░▀░░░░█░█░░░░░
// ░░░░░░█░█░░░░░░░░▄▀▀▄░▀░█░█▄▀▀▄░
// █▀▀█▄░█░█░░▀░░░░░█░░░▀▄▄█▄▀░░░█░
// ▀▄▄░▀██░█▄░▀░░░▄▄▀░░░░░░░░░░░░▀▄
// ░░▀█▄▄█░█░░░░▄░░█░░░▄█░░░▄░▄█░░█
// ░░░░░▀█░▀▄▀░░░░░█░██░▄░░▄░░▄░███
// ░░░░░▄█▄░░▀▀▀▀▀▀▀▀▄░░▀▀▀▀▀▀▀░▄▀░
// ░░░░█░░▄█▀█▀▀█▀▀▀▀▀▀█▀▀█▀█▀▀█░░░
// ░░░░▀▀▀▀░░▀▀▀░░░░░░░░▀▀▀░░▀▀░░░░

#include <bits/stdc++.h>
#include <valarray>
using namespace std;

bool dbg = 0;

// clock_t start_time = clock();
#define current_time fixed<<setprecision(6)<<(ld)(clock()-start_time)/CLOCKS_PER_SEC

#define f first
#define s second
#define mp make_pair
#define pb push_back
#define all(x) (x).begin(), (x).end()

#define ll long long
#define ld long double
#define pii pair<int,int>

#define files1 freopen("input.txt","r",stdin)
#define files2 freopen("output.txt","w",stdout)
#define files files1;files2
#define fast_io ios_base::sync_with_stdio(0);cin.tie(0)

#define endl '\n'
#define ln(i,n) " \n"[(i) == (n) - 1]

void bad(string mes = "Impossible"){cout << mes;exit(0);}
void bad(int mes){cout << mes;exit(0);}

template<typename T>
string bin(T x, int st = 2){
    string ans = "";
    while (x > 0){
        ans += char('0' + x % st);
        x /= st;
    }
    reverse(ans.begin(), ans.end());
    return ans.empty() ? "0" : ans;
}

template<typename T>
void amax(T& x, T y) {
    x = max(x, y);
}

template<typename T>
void amin(T& x, T y) {
    x = min(x, y);
}

template<typename T>
T input(){
    T ans = 0, m = 1;
    char c = ' ';

    while (!((c >= '0' && c <= '9') || c == '-')) {
        c = getchar();
    }

    if (c == '-')
        m = -1, c = getchar();
    while (c >= '0' && c <= '9'){
        ans = ans * 10 + (c - '0'), c = getchar();
    }
    return ans * m;
}

template<typename T> void read(T& a) { a = input<T>(); }
template<typename T> void read(T& a, T& b) { read(a), read(b); }
template<typename T> void read(T& a, T& b, T& c) { read(a, b), read(c); }
template<typename T> void read(T& a, T& b, T& c, T& d) { read(a, b), read(c, d); }

const int inf = 2e9 + 20;
const long double eps = 1e-12;
const int maxn = 1e5 + 12, base = 1e9 + 7;
const ll llinf = 4e18 + 5;

template<typename T>
T binpow(T n, T s)
{
    if (s <= 0)
        return 1LL;
    if (s % 2 == 0){
        T b = binpow(n, s / 2);
        return ( 1LL * b * b ) % base;
    } else {
        return (1LL* binpow(n, s - 1) * n) % base;
    }
}

int a[maxn];

int tree[4 * maxn];
void update(int v, int tl, int tr, int pos, int val) {
    if (tl == tr) tree[v] = val;
    else {
        int m = (tl+tr)>>1;
        if (pos <= m) update(v<<1, tl, m, pos, val); else update(v<<1|1, m + 1, tr, pos, val);
        tree[v] = min(tree[v<<1], tree[v<<1|1]);
    }
}

int get(int v, int tl, int tr, int l, int r) {
    if (l > r) return inf;
    if (tl == l && tr == r) return tree[v];
    int m = (tl+tr)>>1;
    return min(get(v<<1, tl, m, l, min(r, m)), get(v<<1|1, m + 1, tr, max(l, m + 1), r));
}

multiset<int> st;
int cur() {
    if (st.empty()) return -1;
    return *st.rbegin() - *st.begin();
}

int main() {
    int n, s, l;
    read(n, s, l);

    for (int i = 0; i < n; i++) {
        read(a[i]);
    }

    if (l > n) bad(-1);
    for (int i = 0; i + 1 < l; i++) {
        st.insert(a[i]);
        update(1, 0, n - 1, i, inf);
    }

    if (cur() > s) bad(-1);

    int L = 0;
    for (int i = l - 1; i < n; i++) {
        st.insert(a[i]);
        while (cur() > s) {
            st.erase(st.find(a[L]));
            L++;
        }
        if (i - l < L - 1) {
            update(1, 0, n - 1, i, inf);
            continue;
        }
        if (L == 0) {
            // cout << "kek";
            update(1, 0, n - 1, i, 1);
            continue;
        }
        // cout << L - 1 << ' ' << i - l << endl;
        int cur = get(1, 0, n - 1, L - 1, i - l) + 1;
        // cout << i << ' ' << cur
        update(1, 0, n - 1, i, cur);
    }
    int ans = get(1, 0, n - 1, n - 1, n - 1);
    if (ans == inf) ans = -1;
    cout << ans;
    return 0;
}


# include <bits/stdc++.h>
# define ll long long
# define se second
# define fr first
using namespace std;
pair<ll , ll> t[1000010];
ll a[100010] , us[100010] , dp[100010] , p[1000010] , si[1000010];
void stro(ll tv , ll tl , ll tr){
    if(tl == tr) {t[tv].fr = a[tl] , t[tv].se = a[tl];return ;}
    ll tm = (tl + tr) / 2;
    stro(tv * 2 , tl , tm);
    stro(tv * 2 + 1 , tm + 1 , tr);
    t[tv].fr = min(t[tv * 2].fr , t[tv * 2 + 1].fr);
    t[tv].se = max(t[tv * 2].se , t[tv * 2 + 1].se);
}
void build(ll tv , ll tl , ll tr){
    p[tv] = 1000000000;
    if(tl == tr) {si[tv] = dp[tl];return ;}
    ll tm = (tl + tr) / 2;
    build(tv * 2 , tl , tm);
    build(tv * 2 + 1 , tm + 1 , tr);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll ans_min(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 2000000000;
    if(tl == l && tr == r) return t[tv].fr;
    ll tm = (tl + tr) / 2;
    return min(ans_min(tv * 2 , tl , tm , l , min(tm , r)) , ans_min(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
ll ans_max(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 0;
    if(tl == l && tr == r) return t[tv].se;
    ll tm = (tl + tr) / 2;
    return max(ans_max(tv * 2 , tl , tm , l , min(tm , r)) , ans_max(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
void push(ll tv , ll tl , ll tr){
    if(p[tv] != 1000000000){
        si[tv] = min(p[tv] , si[tv]);
        p[tv * 2] = min(p[tv * 2] , p[tv]);
        p[tv * 2 + 1] = min(p[tv * 2 + 1] , p[tv]);
        p[tv] = 1000000000;
    }
}
void iz(ll tv , ll tl , ll tr , ll l , ll r , ll x){
    if(l > r) return ;
    push(tv * 2 , tl , tr);
    if(tl == l && tr == r){
        p[tv] = min(p[tv] , x);
        push(tv * 2 , tl , tr);
        return ;
    }
    ll tm = (tl + tr) / 2;
    iz(tv * 2 , tl , tm , l , min(tm , r) , x);
    iz(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r , x);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll answe(ll tv , ll tl , ll tr , ll l , ll r){
    push(tv , tl , tr);
    if(l > r) return 1000000000;
    if(tl == l && tr == r) return si[tv];
    ll tm = (tl + tr) / 2;
    return min(answe(tv * 2 , tl , tm , l , min(tm , r)) , answe(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
int main()
{
    ll n , s , l , i , j , p , r , kol = 0;
    cin>> n>> s>> p;
    for(i = 1 ; i <= n ; i ++) cin>> a[i];
    stro(1 , 1 , n);
    ll mx , mn;
    for(i = 1 ; i <= n ; i ++){
            l = i , r = n;
            while(l + 1 < r){
                ll bm = (l + r) / 2;
                mn = ans_min(1 , 1 , n , i , bm);
                mx = ans_max(1 , 1 , n , i , bm);
                if(mx - mn <= s) l = bm;
                else r = bm;
            }
            ll bm = r;
            mn = ans_min(1 , 1 , n , i , bm);
            mx = ans_max(1 , 1 , n , i , bm);
            if(mx - mn <= s) l = bm;
            us[i] = l;
    }
    for(i = 2 ; i <= n ; i ++) dp[i] = 1000000000;
    build(1 , 1 , n);
    for(i = 1 ; i <= n ; i ++){
        //cout<<us[i]<<' '<<i<<' '<<q
        if(us[i] - i + 1 < p) continue;
        dp[i] = answe(1 , 1 , n , i , i);
        iz(1 , 1 , n , i + 1 , us[i] , dp[i] + 1);
        if(us[i] + 1 <= n)
        iz(1 , 1 , n , us[i] + 1 , us[i] + 1 , dp[i] + 1);
    }
    dp[n] = answe(1 , 1 , n , n , n);
    dp[1] = 1;
    if(dp[n] >= 1000000000){cout<<-1;return 0;}
    else cout<<dp[n];
}


# include <bits/stdc++.h>
# define ll int
# define se second
# define fr first
using namespace std;
pair<ll , ll> t[1000010];
ll a[100010] , us[100010] , dp[100010];
void stro(ll tv , ll tl , ll tr){
    if(tl == tr) {t[tv].fr = a[tl] , t[tv].se = a[tl];return ;}
    ll tm = (tl + tr) / 2;
    stro(tv * 2 , tl , tm);
    stro(tv * 2 + 1 , tm + 1 , tr);
    t[tv].fr = min(t[tv * 2].fr , t[tv * 2 + 1].fr);
    t[tv].se = max(t[tv * 2].se , t[tv * 2 + 1].se);
}
ll ans_min(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 2000000000;
    if(tl == l && tr == r) return t[tv].fr;
    ll tm = (tl + tr) / 2;
    return min(ans_min(tv * 2 , tl , tm , l , min(tm , r)) , ans_min(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
ll ans_max(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 0;
    if(tl == l && tr == r) return t[tv].se;
    ll tm = (tl + tr) / 2;
    return max(ans_max(tv * 2 , tl , tm , l , min(tm , r)) , ans_max(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
int main()
{
    ll n , s , l , i , j , p , r , kol = 0;
    cin>> n>> s>> p;
    for(i = 1 ; i <= n ; i ++) cin>> a[i];
    stro(1 , 1 , n);
    ll mx , mn;
    for(i = 1 ; i <= n ; i ++){
            l = i , r = n;
            while(l + 1 < r){
                ll bm = (l + r) / 2;
                mn = ans_min(1 , 1 , n , i , bm);
                mx = ans_max(1 , 1 , n , i , bm);
                if(mx - mn <= s) l = bm;
                else r = bm;
            }
            ll bm = r;
            mn = ans_min(1 , 1 , n , i , bm);
            mx = ans_max(1 , 1 , n , i , bm);
            if(mx - mn <= s) l = bm;
            us[i] = l;
    }
    for(i = 2 ; i <= n ; i ++) dp[i] = 1000000000;
    for(i = 1 ; i <= n ; i ++){
        //cout<<us[i]<<' '<<i<<' '<<q
        if(us[i] - i + 1 < p) continue;
        //cout<<i<<' ';
        for(j = i ; j <= us[i] + 1 ; j ++) dp[j] = min(dp[j] , dp[i] + 1);
    }
    dp[1] = 1;
    if(dp[n] >= 1000000000){cout<<-1;return 0;}
    else cout<<dp[n];
}


# include <bits/stdc++.h>
# define ll int
# define se second
# define fr first
using namespace std;
pair<ll , ll> t[1000010];
ll a[100010] , us[100010] , dp[100010];
void stro(ll tv , ll tl , ll tr){
    if(tl == tr) {t[tv].fr = a[tl] , t[tv].se = a[tl];return ;}
    ll tm = (tl + tr) / 2;
    stro(tv * 2 , tl , tm);
    stro(tv * 2 + 1 , tm + 1 , tr);
    t[tv].fr = min(t[tv * 2].fr , t[tv * 2 + 1].fr);
    t[tv].se = max(t[tv * 2].se , t[tv * 2 + 1].se);
}
ll ans_min(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 2000000000;
    if(tl == l && tr == r) return t[tv].fr;
    ll tm = (tl + tr) / 2;
    return min(ans_min(tv * 2 , tl , tm , l , min(tm , r)) , ans_min(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
ll ans_max(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 0;
    if(tl == l && tr == r) return t[tv].se;
    ll tm = (tl + tr) / 2;
    return max(ans_max(tv * 2 , tl , tm , l , min(tm , r)) , ans_max(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
int main()
{
    ll n , s , l , i , j , p , r , kol = 0;
    cin>> n>> s>> p;
    for(i = 1 ; i <= n ; i ++) cin>> a[i];
    stro(1 , 1 , n);
    ll mx , mn;
    for(i = 1 ; i <= n ; i ++){
            l = i , r = n;
            while(l + 1 < r){
                ll bm = (l + r) / 2;
                mn = ans_min(1 , 1 , n , i , bm);
                mx = ans_max(1 , 1 , n , i , bm);
                if(mx - mn <= s) l = bm;
                else r = bm;
            }
            ll bm = r;
            mn = ans_min(1 , 1 , n , i , bm);
            mx = ans_max(1 , 1 , n , i , bm);
            if(mx - mn <= s) l = bm;
            us[i] = l;
    }
    for(i = 2 ; i <= n ; i ++) dp[i] = 1000000000;
    for(i = 1 ; i <= n ; i ++){
        //cout<<us[i]<<' '<<i<<' '<<q
        if(us[i] - i + 1 < p) continue;
        //cout<<i<<' ';
        for(j = i ; j <= us[i] + 1 ; j ++) dp[j] = min(dp[j] , dp[i] + 1);
    }
    if(dp[n] >= 1000000000){cout<<-1;return 0;}
    else cout<<dp[n];
}


# include <bits/stdc++.h>
# define ll int
# define se second
# define fr first
using namespace std;
pair<ll , ll> t[1000010];
ll a[100010] , us[100010] , dp[100010] , p[100010] , si[100010];
void stro(ll tv , ll tl , ll tr){
    if(tl == tr) {t[tv].fr = a[tl] , t[tv].se = a[tl];return ;}
    ll tm = (tl + tr) / 2;
    stro(tv * 2 , tl , tm);
    stro(tv * 2 + 1 , tm + 1 , tr);
    t[tv].fr = min(t[tv * 2].fr , t[tv * 2 + 1].fr);
    t[tv].se = max(t[tv * 2].se , t[tv * 2 + 1].se);
}
void build(ll tv , ll tl , ll tr){
    p[tv] = 1000000000;
    if(tl == tr) {si[tv] = dp[tl];return ;}
    ll tm = (tl + tr) / 2;
    build(tv * 2 , tl , tm);
    build(tv * 2 + 1 , tm + 1 , tr);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll ans_min(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 2000000000;
    if(tl == l && tr == r) return t[tv].fr;
    ll tm = (tl + tr) / 2;
    return min(ans_min(tv * 2 , tl , tm , l , min(tm , r)) , ans_min(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
ll ans_max(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 0;
    if(tl == l && tr == r) return t[tv].se;
    ll tm = (tl + tr) / 2;
    return max(ans_max(tv * 2 , tl , tm , l , min(tm , r)) , ans_max(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
void push(ll tv , ll tl , ll tr){
    if(p[tv] != 1000000000){
        si[tv] = min(p[tv] , si[tv]);
        p[tv * 2] = min(p[tv * 2] , p[tv]);
        p[tv * 2 + 1] = min(p[tv * 2 + 1] , p[tv]);
        p[tv] = 1000000000;
    }
}
void iz(ll tv , ll tl , ll tr , ll l , ll r , ll x){
    if(l > r) return ;
    push(tv * 2 , tl , tr);
    if(tl == l && tr == r){
        p[tv] = min(p[tv] , x);
        push(tv * 2 , tl , tr);
        return ;
    }
    ll tm = (tl + tr) / 2;
    iz(tv * 2 , tl , tm , l , min(tm , r) , x);
    iz(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r , x);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll answe(ll tv , ll tl , ll tr , ll l , ll r){
    push(tv , tl , tr);
    if(l > r) return 1000000000;
    if(tl == l && tr == r) return si[tv];
    ll tm = (tl + tr) / 2;
    return min(answe(tv * 2 , tl , tm , l , min(tm , r)) , answe(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
int main()
{
    ll n , s , l , i , j , p , r , kol = 0;
    cin>> n>> s>> p;
    for(i = 1 ; i <= n ; i ++) cin>> a[i];
    stro(1 , 1 , n);
    ll mx , mn;
    for(i = 1 ; i <= n ; i ++){
            l = i , r = n;
            while(l + 1 < r){
                ll bm = (l + r) / 2;
                mn = ans_min(1 , 1 , n , i , bm);
                mx = ans_max(1 , 1 , n , i , bm);
                if(mx - mn <= s) l = bm;
                else r = bm;
            }
            ll bm = r;
            mn = ans_min(1 , 1 , n , i , bm);
            mx = ans_max(1 , 1 , n , i , bm);
            if(mx - mn <= s) l = bm;
            us[i] = l;
    }
    for(i = 2 ; i <= n ; i ++) dp[i] = 1000000000;
    build(1 , 1 , n);
    for(i = 1 ; i <= n ; i ++){
        //cout<<us[i]<<' '<<i<<' '<<q
        if(us[i] - i + 1 < p) continue;
        dp[i] = answe(1 , 1 , n , i , i);
        iz(1 , 1 , n , i + 1 , us[i] , dp[i] + 1);
        if(us[i] + 1 <= n)
        iz(1 , 1 , n , us[i] + 1 , us[i] + 1 , dp[i] + 1);
    }
    dp[n] = answe(1 , 1 , n , n , n);
    dp[1] = 1;
    if(dp[n] >= 1000000000){cout<<-1;return 0;}
    else cout<<dp[n];
}


# include <bits/stdc++.h>
# define ll int
# define se second
# define fr first
using namespace std;
pair<ll , ll> t[1000010];
ll a[100010] , us[100010] , dp[100010] , p[1000010] , si[1000010];
void stro(ll tv , ll tl , ll tr){
    if(tl == tr) {t[tv].fr = a[tl] , t[tv].se = a[tl];return ;}
    ll tm = (tl + tr) / 2;
    stro(tv * 2 , tl , tm);
    stro(tv * 2 + 1 , tm + 1 , tr);
    t[tv].fr = min(t[tv * 2].fr , t[tv * 2 + 1].fr);
    t[tv].se = max(t[tv * 2].se , t[tv * 2 + 1].se);
}
void build(ll tv , ll tl , ll tr){
    p[tv] = 1000000000;
    if(tl == tr) {si[tv] = dp[tl];return ;}
    ll tm = (tl + tr) / 2;
    build(tv * 2 , tl , tm);
    build(tv * 2 + 1 , tm + 1 , tr);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll ans_min(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 2000000000;
    if(tl == l && tr == r) return t[tv].fr;
    ll tm = (tl + tr) / 2;
    return min(ans_min(tv * 2 , tl , tm , l , min(tm , r)) , ans_min(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
ll ans_max(ll tv , ll tl , ll tr , ll l , ll r){
    if(l > r) return 0;
    if(tl == l && tr == r) return t[tv].se;
    ll tm = (tl + tr) / 2;
    return max(ans_max(tv * 2 , tl , tm , l , min(tm , r)) , ans_max(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
void push(ll tv , ll tl , ll tr){
    if(p[tv] != 1000000000){
        si[tv] = min(p[tv] , si[tv]);
        p[tv * 2] = min(p[tv * 2] , p[tv]);
        p[tv * 2 + 1] = min(p[tv * 2 + 1] , p[tv]);
        p[tv] = 1000000000;
    }
}
void iz(ll tv , ll tl , ll tr , ll l , ll r , ll x){
    if(l > r) return ;
    push(tv * 2 , tl , tr);
    if(tl == l && tr == r){
        p[tv] = min(p[tv] , x);
        push(tv * 2 , tl , tr);
        return ;
    }
    ll tm = (tl + tr) / 2;
    iz(tv * 2 , tl , tm , l , min(tm , r) , x);
    iz(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r , x);
    si[tv] = min(si[tv * 2] , si[tv * 2 + 1]);
}
ll answe(ll tv , ll tl , ll tr , ll l , ll r){
    push(tv , tl , tr);
    if(l > r) return 1000000000;
    if(tl == l && tr == r) return si[tv];
    ll tm = (tl + tr) / 2;
    return min(answe(tv * 2 , tl , tm , l , min(tm , r)) , answe(tv * 2 + 1 , tm + 1 , tr , max(tm + 1 , l) , r));
}
int main()
{
    ll n , s , l , i , j , p , r , kol = 0;
    cin>> n>> s>> p;
    for(i = 1 ; i <= n ; i ++) cin>> a[i];
    stro(1 , 1 , n);
    ll mx , mn;
    for(i = 1 ; i <= n ; i ++){
            l = i , r = n;
            while(l + 1 < r){
                ll bm = (l + r) / 2;
                mn = ans_min(1 , 1 , n , i , bm);
                mx = ans_max(1 , 1 , n , i , bm);
                if(mx - mn <= s) l = bm;
                else r = bm;
            }
            ll bm = r;
            mn = ans_min(1 , 1 , n , i , bm);
            mx = ans_max(1 , 1 , n , i , bm);
            if(mx - mn <= s) l = bm;
            us[i] = l;
    }
    for(i = 2 ; i <= n ; i ++) dp[i] = 1000000000;
    build(1 , 1 , n);
    for(i = 1 ; i <= n ; i ++){
        //cout<<us[i]<<' '<<i<<' '<<q
        if(us[i] - i + 1 < p) continue;
        dp[i] = answe(1 , 1 , n , i , i);
        iz(1 , 1 , n , i + 1 , us[i] , dp[i] + 1);
        if(us[i] + 1 <= n)
        iz(1 , 1 , n , us[i] + 1 , us[i] + 1 , dp[i] + 1);
    }
    dp[n] = answe(1 , 1 , n , n , n);
    dp[1] = 1;
    if(dp[n] >= 1000000000){cout<<-1;return 0;}
    else cout<<dp[n];
}


#include <iostream>
#include <stdio.h>
#include <math.h>
#include <algorithm>
#include <string>
#include <vector>
#include <map>
#include <queue>
#include <string>

#define fi first
#define se second
#define pb push_back
#define mk make_pair
#define Pii pair < int , int >
#define tree int t,int l,int r
#define left 2*t,l,(l+r)/2
#define right 2*t+1,(l+r)/2+1,r
#define f_sum(i,r) for (int i=r;i>=0;i=(i&(i+1))-1)
#define f_upd(i,a,r) for (int i=a;i<=r;i=(i|(i+1)))
#define MA(a,b) ((a)>(b)?(a):(b))
#define MI(a,b) ((a)<(b)?(a):(b))
#define AB(a) (-(a)<(a)?(a):-(a))
#define ged(x) scanf("%I64d",&x)
#define getcx getchar//_unlocked
#define put(x) cout<<x<<endl;
#define pud(x) printf("%.12f\n",x);
#define LL long long
#define INF 1000000000
#define eps 0.00000001
#define P7 1000000007
#define P9 1000000009
#define N3 2555
#define N5 262145

using namespace std;

inline void inp(int &n )
 {n=0; int ch=getcx();int sign=1;
  while(ch<'0'||ch>'9'){if(ch=='-')sign=-1; ch=getcx();}
  while(  ch >= '0' && ch <= '9' ) n=(n<<3)+(n<<1)+ch-'0',ch=getcx();
  n=n*sign;}

int tst;
void get_ready() {
     //freopen(".in","r",stdin);
     //freopen(".out","w",stdout);
     tst=1; //inp(tst);
}

int mi[N5],ma[N5],tr[N5],ans[N5],a[N5],la,mii,maa;

void build (tree)
 {
  if (l == r)
  {
   ma[t]=a[l];
   mi[t]=a[l];
   return ;
  }
  build (left);
  build (right);
  ma[t]=MA(ma[2*t],ma[2*t+1]);
  mi[t]=MI(mi[2*t],mi[2*t+1]);
 }

void get_mi(tree,int L,int R)
 {
  if (l > R || L > r) return;
  if (L <= l && r <= R) { la=MI(la,tr[t]); return; }
  get_mi(left,L,R);
  get_mi(right,L,R);
 }

void get_m(tree,int L,int R)
 {
  if (l > R || L > r) return;
  if (L <= l && r <= R) { mii=MI(mii,mi[t]); maa=MA(maa,ma[t]); return; }
  get_m(left,L,R);
  get_m(right,L,R);
 }

void upd_mi(tree,int i,int la)
 {
  if (l > i || i > r) return;
  if (l == r) { tr[t]=la; return; }
  upd_mi(left,i,la);
  upd_mi(right,i,la);
  tr[t]=MI(tr[2*t],tr[2*t+1]);
 }

int n,s,L,i;

main()
 {
     int ans =0;
 cin>>n>>s>>L;
for (i=1;i<=n;i++)
     cin>>a[i];
 build(1,1,n);
 for (i=1;i<=n;i++)
  {
   int l=1,r=i,m=0,mid=-1;
   while (l <= r)
    {
     m=(l+r)/2;
     mii=INF;
     maa=-INF;
     get_m(1,1,n,m,i);
     if (maa-mii <= s) { mid=m; r=m-1; } else l=m+1;
    }
   mid=mid-1;
   la=INF;
   get_mi(1,0,n,mid,i-L);
   upd_mi(1,0,n,i,la+1);
   ans = la+1;
  /* for(int j = 1 ; j <= n ; j ++) cout<< ans[j]<<' ';
   cout<<'\n';*/
  }
if (ans >= INF) ans=-1;
cout<<ans<<endl;
 }


#include <bits/stdc++.h>
#define N 100007
using namespace std;

multiset<int> st,rt;
int dp[N],n,l,s,a[N];

int main()
{
	cin>>n>>s>>l;
	for(int i=1;i<=n;i++) scanf("%d",a+i);
	for(int i=1,j=1;i<=n;i++)
	{
		st.insert(a[i]);
		for(;*st.rbegin()-*st.begin()>s;j++)
		{
			st.erase(st.find(a[j]));
			if(i-j>=l) rt.erase(rt.find(dp[j-1]));
		}
		if(i-j+1>=l) rt.insert(dp[i-l]);
		if(rt.begin()==rt.end()) dp[i]=N;
		else dp[i]=*rt.begin()+1;
	}
	cout<<(dp[n]>=N?-1:dp[n])<<endl;
	return 0;
}


#include <bits/stdc++.h>
#define INF 1000000000

using namespace std;

const int N = 1e5 + 5;
//int tr[N];
//int get(int idx){
//  int res = 0;
//  while(idx){
//    res += tr[idx];
//    idx -= (idx & -idx);
//  }
//  return res;
//}
//void add(int idx, int val){
//  while(idx<N){
//    tr[idx] += val;
//    idx += (idx & -idx);
//  }
//}

struct MQ{
  queue<int> qu;
  deque<int> mx;
  void push(int val){
    qu.push(val);
    while(mx.size() && mx.back()<val) mx.pop_back();
    mx.push_back(val);
  }
  void pop(){
    if(qu.front()==mx.front())
      mx.pop_front();
    qu.pop();
  }
  int top(){
    return qu.front();
  }
  int getMax(){
    return mx.front();
  }
  int size(){
    return qu.size();
  }
};

int n, s, l, srt[N], arr[N], dp[N], seg[N];

void insrt(int idx, int val, int s=0, int e=n, int p=1){
  if(s==e){
    seg[p] = val;
    return;
  }
  int mid = (s+e)>>1;
  if(idx<=mid) insrt(idx, val, s, mid, p<<1);
  else insrt(idx, val, mid+1, e, p<<1|1);
  seg[p] = min(seg[p<<1], seg[p<<1|1]);
}

int query(int l, int r, int s=0, int e=n, int p=1){
  if(s>=l && e<=r) return seg[p];
  int mid = (s+e)>>1;
//  cout << s << " " << e << "--" << l << " " << r << endl;
  if(r<=mid)
    return query(l, r, s, mid, p<<1);
  else if(l>mid)
    return query(l, r, mid+1, e, p<<1|1);
  else
    return min(query(l, r, s, mid, p<<1), query(l, r, mid+1, e, p<<1|1));
}

int main() {

//  freopen("e_high_bonus.in", "r", stdin);
//  freopen("e_high_bonus.out", "w", stdout);
	cin.sync_with_stdio(0);

	cin >> n >> s >> l;
	for(int i=1; i<=n; i++)
    cin >> arr[i];
  int nxt = n;
  MQ mn, mx;
  for(int i=n; i; i--){
    srt[i] = -1;
    while(nxt && ( mx.size()==0 || (mx.getMax()-arr[nxt]<=s && arr[nxt]+mn.getMax()<=s))){
      mx.push(arr[nxt]);
      mn.push(-arr[nxt--]);
    }
    mx.pop();
    mn.pop();
    if(i-nxt>=l)
      srt[i] = nxt + 1;
  }
  for(int i=1; i<=n; i++)
    insrt(i, INF);
  insrt(0, 0);
  for(int i=1; i<=n; i++){
    dp[i] = INF;
    if(srt[i]==-1) continue;
    dp[i] = query(srt[i]-1, i-l) + 1;
//    cout << srt[i]-1 << " " << i-l << " " << dp[i] << endl;
    insrt(i, dp[i]);
  }
  if(dp[n]>=INF)
    puts("-1");
  else
    cout << dp[n] << endl;

  return 0;
}


#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
#define mod 1000000007
#include<string.h>
#define inf 10000000000000000
#define maxn 400006
typedef pair<ll,ll> pll;
typedef pair<int,int> pint;
#define pi 3.14159265359
#define endl '\n'
#define mapint_iterator map<int,int> :: iterator
#define mapll_iterator map<ll,ll> :: iterator
#define setint_iterator set<int> :: iterator
#define setll_iterator set<ll> :: iterator
#define setpint_iterator set<pint> :: iterator
#define setpll_iterator set<pll> :: iterator
#define trace(x) cout<<#x<<": "<<x<<" "<<endl
#define trace2(x,y) cout<<#x<<": "<<x<<" | "<<#y<<": "<<y<<endl
#define trace3(x,y,z) cout<<#x<<":" <<x<<" | "<<#y<<": "<<y<<" | "<<#z<<": "<<z<<endl
#define trace4(a,b,c,d) cout<<#a<<": "<<a<<" | "<<#b<<": "<<b<<" | "<<#c<<": "<<c<<" | "<<#d<<": "<<d<<endl
#define cout1(a) cout<<a<<endl
#define cout2(a,b) cout<<a<<' '<<b<<endl
#define cout3(a,b,c) cout<<a<<" "<<b<<" "<<c<<endl
#define cout4(a,b,c,d) cout<<a<<" "<<b<<" "<<c<<" "<<d<<endl
#define vcout(v,i) cout<<v[i].fi<<" "<<v[i].se<<endl
typedef priority_queue<ll,vector<ll>,greater<ll> > pqset;
typedef priority_queue<pint,vector<pint>,greater<pint> > pqset_ll;
#define pb push_back
#define pf push_front
#define fi first
#define se second
ll dxk[]={0,0,1,-1,1,1,-1,-1};
ll dyk[]={1,-1,0,0,1,-1,1,-1};
/*
#include<ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
typedef tree<int,null_type,less<int>,rb_tree_tag,tree_order_statistics_node_update> os;
typedef tree<pll,null_type,less<pll>,rb_tree_tag,tree_order_statistics_node_update> os_pair;
#define acc (ios::sync_with_stdio(false),cin.tie(0))
*/
#define rep(i,n) for(ll i=0;i<n;i++)
#define per(i,n) for(ll i=n-1;i>=0;i--)
#define rep1(i,n) for(ll i=1;i<=n;i++)
#define per1(i,n) for(ll i=n;i>0;i--)
#define repeat(i,start,n) for(ll i=start;i<n;i++)
#define print(a,n) for(ll i=0;i<n;i++){ cout<<a[i]<<" ";}
ll ll_max(ll a,ll b,ll c){return max(a,max(b,c));}
int int_max(int a,int b,int c){return max(a,max(b,c));}
ll ll_min(ll a,ll b,ll c){return min(a,min(b,c));}
int int_min(int a,int b,int c){return min(a,min(b,c));}
ll max(int a,ll b){ return max((ll)a,b);}
ll min(int a,ll b){ return min((ll)a,b);}
ll min(ll a,int b){ return min(a,(ll)b);}
ll max(ll a,int b){ return max(a,(ll)b);}
ll dx[]={0,0,1,-1};
ll dy[]={1,-1,0,0};
ll power(ll a,ll b){
	if(a==1)
		return 1;
	if(b==0)
		return 1;
	ll c=power(a,b/2);
	ll res=1;
	if(b%2){
		res=(c*c)%mod;
		res*=a;
		res%=mod;
	}
	else
		res=((c*c)%mod);
	return res;
}
ll modInv(ll a){return power(a,mod-2)%mod;}
ll fact[1],inv[1];
void factorial(ll n){
	fact[0]=1;
	for(ll i=1;i<=n;i++){
		fact[i]=fact[i-1]*i;
		fact[i]%=mod;
	}
}
void InvFactorial(ll n){
	inv[0]=1;
	for(ll i=1;i<=n;i++)
		inv[i]=modInv(fact[i]);
}
ll ncr(ll n,ll r){
	if(n<r||n<0||r<0)
		return 0;
	ll b=inv[n-r];
	ll c=inv[r];
	ll a=fact[n]*b;
	a%=mod;
	a*=c;
	a%=mod;
	return a;
}
//ifstream cin("b_read_on.txt"); ofstream cout("output3.txt");
//Chronology: Binary Search,Greedy,dp,dfs and similar
//Use (<<) for multiplication
//Use (>>) for division
//If memory limit exceeds in top-down , try bottom up dp
//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);
// find_by_order -> value at index
// order_of_key -> index of value
// while using (1<<i) use ((ll)1<<(ll)i)
// if global declared initialise per testcase
// in Floyd-Warshall Algo, k is outer loop
//pair is initialised as {0,0}
//value of dp array is not the same in top-down & bottom-up
// If an element was not initially in map and if asked mp[a],the element gets inserted
// Dont use unordered_map until necessary
ll n,s,l;
ll a[100001];
int dp1[100001];
ll Tree[400001],Tree1[400001];
void build_max(int node,int start,int end){
	if(start==end){
		Tree[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_max(2*node+1,start,mid);
	build_max(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree[node]=max(Tree[2*node+1],Tree[2*node+2]);
}
ll query_max(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return -10000000000;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_max(node*2+1, start, mid, l,r);
	ll p2 = query_max(node*2+2, mid+1, end , l,r);
	return max(p1,p2);
}
void build_min(int node,int start,int end){
	if(start==end){
		Tree1[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_min(2*node+1,start,mid);
	build_min(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
void update_min(int node,int start,int end,int i,ll val){
	if(start==end){
		Tree1[node]=val;
		return;
	}
	int mid=((start+end)>>1);
	if(i<=mid)
		update_min(2*node+1,start,mid,i,val);
	else
		update_min(2*node+2,mid+1,end,i,val);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
ll query_min(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 100000000000000;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree1[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_min(node*2+1, start, mid, l,r);
	ll p2 = query_min(node*2+2, mid+1, end , l,r);
	return min(p1,p2);
}
ll dp[100001];
void solve(int countu){
	cin>>n>>s>>l;
	rep(i,n){
		scanf("%lld",&a[i]);
	}
	if(l>n){
		cout1(-1);
		return;
	}
	ll minn,maxx,j=n-2;
	build_max(0,0,n-1);
	build_min(0,0,n-1);
	for(int i=n-1;i>=0;i--){
		maxx=query_max(0,0,n-1,j+1,i);
		minn=query_min(0,0,n-1,j+1,i);
		while(j>=0){
			ll maxx1=max(maxx,a[j]);
			ll minn1=min(minn,a[j]);
			if(maxx1-minn1<=s){
				maxx=maxx1;
				minn=minn1;
				j--;
				continue;
			}
			break;
		}
		dp1[i]=max(0,j);
	}
	ll k=query_max(0,0,n-1,0,l-1)-query_min(0,0,n-1,0,l-1);
	memset(Tree1,0,sizeof(Tree1));
	repeat(i,1,l-1)
		update_min(0,0,n-1,i,inf);
	if(k<=s)
		update_min(0,0,n-1,l-1,1);
	else
		update_min(0,0,n-1,l-1,inf);
	repeat(i,l,n){
		if(dp1[i]>i-l){
			update_min(0,0,n-1,i,inf);
			continue;
		}
		ll j=query_min(0,0,n-1,dp1[i],i-l);
		j++;
		update_min(0,0,n-1,i,j);
	}
	if(query_min(0,0,n-1,n-1,n-1)>=1e12)
		cout1(-1);
	else
		cout1(query_min(0,0,n-1,n-1,n-1));
}
int main(){
	//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);cout.precision(10);
	int t=1;
	//scanf("%d",&t);
	int countu=1;
    while(t--){
    	solve(countu);
    	countu++;
    }
}


#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
#define mod 1000000007
#include<string.h>
#define inf 10000000000000000
#define maxn 400006
typedef pair<ll,ll> pll;
typedef pair<int,int> pint;
#define pi 3.14159265359
#define endl '\n'
#define mapint_iterator map<int,int> :: iterator
#define mapll_iterator map<ll,ll> :: iterator
#define setint_iterator set<int> :: iterator
#define setll_iterator set<ll> :: iterator
#define setpint_iterator set<pint> :: iterator
#define setpll_iterator set<pll> :: iterator
#define trace(x) cout<<#x<<": "<<x<<" "<<endl
#define trace2(x,y) cout<<#x<<": "<<x<<" | "<<#y<<": "<<y<<endl
#define trace3(x,y,z) cout<<#x<<":" <<x<<" | "<<#y<<": "<<y<<" | "<<#z<<": "<<z<<endl
#define trace4(a,b,c,d) cout<<#a<<": "<<a<<" | "<<#b<<": "<<b<<" | "<<#c<<": "<<c<<" | "<<#d<<": "<<d<<endl
#define cout1(a) cout<<a<<endl
#define cout2(a,b) cout<<a<<' '<<b<<endl
#define cout3(a,b,c) cout<<a<<" "<<b<<" "<<c<<endl
#define cout4(a,b,c,d) cout<<a<<" "<<b<<" "<<c<<" "<<d<<endl
#define vcout(v,i) cout<<v[i].fi<<" "<<v[i].se<<endl
typedef priority_queue<ll,vector<ll>,greater<ll> > pqset;
typedef priority_queue<pint,vector<pint>,greater<pint> > pqset_ll;
#define pb push_back
#define pf push_front
#define fi first
#define se second
ll dxk[]={0,0,1,-1,1,1,-1,-1};
ll dyk[]={1,-1,0,0,1,-1,1,-1};
/*
#include<ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
typedef tree<int,null_type,less<int>,rb_tree_tag,tree_order_statistics_node_update> os;
typedef tree<pll,null_type,less<pll>,rb_tree_tag,tree_order_statistics_node_update> os_pair;
#define acc (ios::sync_with_stdio(false),cin.tie(0))
*/
#define rep(i,n) for(ll i=0;i<n;i++)
#define per(i,n) for(ll i=n-1;i>=0;i--)
#define rep1(i,n) for(ll i=1;i<=n;i++)
#define per1(i,n) for(ll i=n;i>0;i--)
#define repeat(i,start,n) for(ll i=start;i<n;i++)
#define print(a,n) for(ll i=0;i<n;i++){ cout<<a[i]<<" ";}
ll ll_max(ll a,ll b,ll c){return max(a,max(b,c));}
int int_max(int a,int b,int c){return max(a,max(b,c));}
ll ll_min(ll a,ll b,ll c){return min(a,min(b,c));}
int int_min(int a,int b,int c){return min(a,min(b,c));}
ll max(int a,ll b){ return max((ll)a,b);}
ll min(int a,ll b){ return min((ll)a,b);}
ll min(ll a,int b){ return min(a,(ll)b);}
ll max(ll a,int b){ return max(a,(ll)b);}
ll dx[]={0,0,1,-1};
ll dy[]={1,-1,0,0};
ll power(ll a,ll b){
	if(a==1)
		return 1;
	if(b==0)
		return 1;
	ll c=power(a,b/2);
	ll res=1;
	if(b%2){
		res=(c*c)%mod;
		res*=a;
		res%=mod;
	}
	else
		res=((c*c)%mod);
	return res;
}
ll modInv(ll a){return power(a,mod-2)%mod;}
ll fact[1],inv[1];
void factorial(ll n){
	fact[0]=1;
	for(ll i=1;i<=n;i++){
		fact[i]=fact[i-1]*i;
		fact[i]%=mod;
	}
}
void InvFactorial(ll n){
	inv[0]=1;
	for(ll i=1;i<=n;i++)
		inv[i]=modInv(fact[i]);
}
ll ncr(ll n,ll r){
	if(n<r||n<0||r<0)
		return 0;
	ll b=inv[n-r];
	ll c=inv[r];
	ll a=fact[n]*b;
	a%=mod;
	a*=c;
	a%=mod;
	return a;
}
//ifstream cin("b_read_on.txt"); ofstream cout("output3.txt");
//Chronology: Binary Search,Greedy,dp,dfs and similar
//Use (<<) for multiplication
//Use (>>) for division
//If memory limit exceeds in top-down , try bottom up dp
//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);
// find_by_order -> value at index
// order_of_key -> index of value
// while using (1<<i) use ((ll)1<<(ll)i)
// if global declared initialise per testcase
// in Floyd-Warshall Algo, k is outer loop
//pair is initialised as {0,0}
//value of dp array is not the same in top-down & bottom-up
// If an element was not initially in map and if asked mp[a],the element gets inserted
// Dont use unordered_map until necessary
ll n,s,l;
ll a[100001];
int dp1[100001];
ll Tree[400001],Tree1[400001];
void build_max(int node,int start,int end){
	if(start==end){
		Tree[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_max(2*node+1,start,mid);
	build_max(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree[node]=max(Tree[2*node+1],Tree[2*node+2]);
}
ll query_max(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 0;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_max(node*2+1, start, mid, l,r);
	ll p2 = query_max(node*2+2, mid+1, end , l,r);
	return max(p1,p2);
}
void build_min(int node,int start,int end){
	if(start==end){
		Tree1[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_min(2*node+1,start,mid);
	build_min(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
void update_min(int node,int start,int end,int i,ll val){
	if(start==end){
		Tree1[node]=val;
		return;
	}
	int mid=((start+end)>>1);
	if(i<=mid)
		update_min(2*node+1,start,mid,i,val);
	else
		update_min(2*node+2,mid+1,end,i,val);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
ll query_min(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 100000000000000;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree1[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_min(node*2+1, start, mid, l,r);
	ll p2 = query_min(node*2+2, mid+1, end , l,r);
	return min(p1,p2);
}
ll dp[100001];
void solve(int countu){
	cin>>n>>s>>l;
	rep(i,n){
		scanf("%lld",&a[i]);
		a[i]+=mod;
	}
	if(l>n){
		cout1(-1);
		return;
	}
	ll minn,maxx,j=n-2;
	build_max(0,0,n-1);
	build_min(0,0,n-1);
	for(int i=n-1;i>=0;i--){
		maxx=query_max(0,0,n-1,j+1,i);
		minn=query_min(0,0,n-1,j+1,i);
		while(j>=0){
			ll maxx1=max(maxx,a[j]);
			ll minn1=min(minn,a[j]);
			if(maxx1-minn1<=s){
				maxx=maxx1;
				minn=minn1;
				j--;
				continue;
			}
			break;
		}
		dp1[i]=max(0,j);
	}
	memset(Tree1,0,sizeof(Tree1));
	repeat(i,1,l-1)
		update_min(0,0,n-1,i,inf);
	if(dp1[l-1]!=0)
		update_min(0,0,n-1,l-1,inf);
	else
		update_min(0,0,n-1,l-1,1);
	repeat(i,l,n){
		if(dp1[i]>i-l){
			update_min(0,0,n-1,i,inf);
			continue;
		}
		ll j=query_min(0,0,n-1,dp1[i],i-l);
		j++;
		update_min(0,0,n-1,i,j);
	}
	if(query_min(0,0,n-1,n-1,n-1)>=1e12)
		cout1(-1);
	else
		cout1(query_min(0,0,n-1,n-1,n-1));
}
int main(){
	//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);cout.precision(10);
	int t=1;
	//scanf("%d",&t);
	int countu=1;
    while(t--){
    	solve(countu);
    	countu++;
    }
}


#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
#define mod 1000000007
#include<string.h>
#define inf 10000000000000000
#define maxn 400006
typedef pair<ll,ll> pll;
typedef pair<int,int> pint;
#define pi 3.14159265359
#define endl '\n'
#define mapint_iterator map<int,int> :: iterator
#define mapll_iterator map<ll,ll> :: iterator
#define setint_iterator set<int> :: iterator
#define setll_iterator set<ll> :: iterator
#define setpint_iterator set<pint> :: iterator
#define setpll_iterator set<pll> :: iterator
#define trace(x) cout<<#x<<": "<<x<<" "<<endl
#define trace2(x,y) cout<<#x<<": "<<x<<" | "<<#y<<": "<<y<<endl
#define trace3(x,y,z) cout<<#x<<":" <<x<<" | "<<#y<<": "<<y<<" | "<<#z<<": "<<z<<endl
#define trace4(a,b,c,d) cout<<#a<<": "<<a<<" | "<<#b<<": "<<b<<" | "<<#c<<": "<<c<<" | "<<#d<<": "<<d<<endl
#define cout1(a) cout<<a<<endl
#define cout2(a,b) cout<<a<<' '<<b<<endl
#define cout3(a,b,c) cout<<a<<" "<<b<<" "<<c<<endl
#define cout4(a,b,c,d) cout<<a<<" "<<b<<" "<<c<<" "<<d<<endl
#define vcout(v,i) cout<<v[i].fi<<" "<<v[i].se<<endl
typedef priority_queue<ll,vector<ll>,greater<ll> > pqset;
typedef priority_queue<pint,vector<pint>,greater<pint> > pqset_ll;
#define pb push_back
#define pf push_front
#define fi first
#define se second
ll dxk[]={0,0,1,-1,1,1,-1,-1};
ll dyk[]={1,-1,0,0,1,-1,1,-1};
/*
#include<ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
typedef tree<int,null_type,less<int>,rb_tree_tag,tree_order_statistics_node_update> os;
typedef tree<pll,null_type,less<pll>,rb_tree_tag,tree_order_statistics_node_update> os_pair;
#define acc (ios::sync_with_stdio(false),cin.tie(0))
*/
#define rep(i,n) for(ll i=0;i<n;i++)
#define per(i,n) for(ll i=n-1;i>=0;i--)
#define rep1(i,n) for(ll i=1;i<=n;i++)
#define per1(i,n) for(ll i=n;i>0;i--)
#define repeat(i,start,n) for(ll i=start;i<n;i++)
#define print(a,n) for(ll i=0;i<n;i++){ cout<<a[i]<<" ";}
ll ll_max(ll a,ll b,ll c){return max(a,max(b,c));}
int int_max(int a,int b,int c){return max(a,max(b,c));}
ll ll_min(ll a,ll b,ll c){return min(a,min(b,c));}
int int_min(int a,int b,int c){return min(a,min(b,c));}
ll max(int a,ll b){ return max((ll)a,b);}
ll min(int a,ll b){ return min((ll)a,b);}
ll min(ll a,int b){ return min(a,(ll)b);}
ll max(ll a,int b){ return max(a,(ll)b);}
ll dx[]={0,0,1,-1};
ll dy[]={1,-1,0,0};
ll power(ll a,ll b){
	if(a==1)
		return 1;
	if(b==0)
		return 1;
	ll c=power(a,b/2);
	ll res=1;
	if(b%2){
		res=(c*c)%mod;
		res*=a;
		res%=mod;
	}
	else
		res=((c*c)%mod);
	return res;
}
ll modInv(ll a){return power(a,mod-2)%mod;}
ll fact[1],inv[1];
void factorial(ll n){
	fact[0]=1;
	for(ll i=1;i<=n;i++){
		fact[i]=fact[i-1]*i;
		fact[i]%=mod;
	}
}
void InvFactorial(ll n){
	inv[0]=1;
	for(ll i=1;i<=n;i++)
		inv[i]=modInv(fact[i]);
}
ll ncr(ll n,ll r){
	if(n<r||n<0||r<0)
		return 0;
	ll b=inv[n-r];
	ll c=inv[r];
	ll a=fact[n]*b;
	a%=mod;
	a*=c;
	a%=mod;
	return a;
}
//ifstream cin("b_read_on.txt"); ofstream cout("output3.txt");
//Chronology: Binary Search,Greedy,dp,dfs and similar
//Use (<<) for multiplication
//Use (>>) for division
//If memory limit exceeds in top-down , try bottom up dp
//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);
// find_by_order -> value at index
// order_of_key -> index of value
// while using (1<<i) use ((ll)1<<(ll)i)
// if global declared initialise per testcase
// in Floyd-Warshall Algo, k is outer loop
//pair is initialised as {0,0}
//value of dp array is not the same in top-down & bottom-up
// If an element was not initially in map and if asked mp[a],the element gets inserted
// Dont use unordered_map until necessary
ll n,s,l;
ll a[100001];
int dp1[100001];
ll Tree[400001],Tree1[400001];
void build_max(int node,int start,int end){
	if(start==end){
		Tree[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_max(2*node+1,start,mid);
	build_max(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree[node]=max(Tree[2*node+1],Tree[2*node+2]);
}
ll query_max(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 0;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_max(node*2+1, start, mid, l,r);
	ll p2 = query_max(node*2+2, mid+1, end , l,r);
	return max(p1,p2);
}
void build_min(int node,int start,int end){
	if(start==end){
		Tree1[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_min(2*node+1,start,mid);
	build_min(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
void update_min(int node,int start,int end,int i,ll val){
	if(start==end){
		Tree1[node]=val;
		return;
	}
	int mid=((start+end)>>1);
	if(i<=mid)
		update_min(2*node+1,start,mid,i,val);
	else
		update_min(2*node+2,mid+1,end,i,val);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
ll query_min(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 100000000000000;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree1[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_min(node*2+1, start, mid, l,r);
	ll p2 = query_min(node*2+2, mid+1, end , l,r);
	return min(p1,p2);
}
ll dp[100001];
void solve(int countu){
	cin>>n>>s>>l;
	rep(i,n)
		scanf("%lld",&a[i]);
	if(l>n){
		cout1(-1);
		return;
	}
	ll minn,maxx,j=n-2;
	build_max(0,0,n-1);
	build_min(0,0,n-1);
	for(int i=n-1;i>=0;i--){
		maxx=query_max(0,0,n-1,j+1,i);
		minn=query_min(0,0,n-1,j+1,i);
		while(j>=0){
			ll maxx1=max(maxx,a[j]);
			ll minn1=min(minn,a[j]);
			if(maxx1-minn1<=s){
				maxx=maxx1;
				minn=minn1;
				j--;
				continue;
			}
			break;
		}
		dp1[i]=max(0,j);
	}
	memset(dp,0,sizeof(dp));
	memset(Tree1,0,sizeof(Tree1));
	repeat(i,1,l-1)
		update_min(0,0,n-1,i,inf);
	if(dp1[l-1]!=0)
		update_min(0,0,n-1,l-1,inf);
	else
		update_min(0,0,n-1,l-1,1);
	repeat(i,l,n){
		if(dp1[i]>i-l){
			update_min(0,0,n-1,i,inf);
			continue;
		}
		ll j=query_min(0,0,n-1,dp1[i],i-l);
		j++;
		update_min(0,0,n-1,i,j);
	}
	if(query_min(0,0,n-1,n-1,n-1)>=1e12)
		cout1(-1);
	else
		cout1(query_min(0,0,n-1,n-1,n-1));
}
int main(){
	//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);cout.precision(10);
	int t=1;
	//scanf("%d",&t);
	int countu=1;
    while(t--){
    	solve(countu);
    	countu++;
    }
}


#include<bits/stdc++.h>
using namespace std;
typedef long long int ll;
#define mod 1000000007
#include<string.h>
#define inf 10000000000000000
#define maxn 400006
typedef pair<ll,ll> pll;
typedef pair<int,int> pint;
#define pi 3.14159265359
#define endl '\n'
#define mapint_iterator map<int,int> :: iterator
#define mapll_iterator map<ll,ll> :: iterator
#define setint_iterator set<int> :: iterator
#define setll_iterator set<ll> :: iterator
#define setpint_iterator set<pint> :: iterator
#define setpll_iterator set<pll> :: iterator
#define trace(x) cout<<#x<<": "<<x<<" "<<endl
#define trace2(x,y) cout<<#x<<": "<<x<<" | "<<#y<<": "<<y<<endl
#define trace3(x,y,z) cout<<#x<<":" <<x<<" | "<<#y<<": "<<y<<" | "<<#z<<": "<<z<<endl
#define trace4(a,b,c,d) cout<<#a<<": "<<a<<" | "<<#b<<": "<<b<<" | "<<#c<<": "<<c<<" | "<<#d<<": "<<d<<endl
#define cout1(a) cout<<a<<endl
#define cout2(a,b) cout<<a<<' '<<b<<endl
#define cout3(a,b,c) cout<<a<<" "<<b<<" "<<c<<endl
#define cout4(a,b,c,d) cout<<a<<" "<<b<<" "<<c<<" "<<d<<endl
#define vcout(v,i) cout<<v[i].fi<<" "<<v[i].se<<endl
typedef priority_queue<ll,vector<ll>,greater<ll> > pqset;
typedef priority_queue<pint,vector<pint>,greater<pint> > pqset_ll;
#define pb push_back
#define pf push_front
#define fi first
#define se second
ll dxk[]={0,0,1,-1,1,1,-1,-1};
ll dyk[]={1,-1,0,0,1,-1,1,-1};
/*
#include<ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
typedef tree<int,null_type,less<int>,rb_tree_tag,tree_order_statistics_node_update> os;
typedef tree<pll,null_type,less<pll>,rb_tree_tag,tree_order_statistics_node_update> os_pair;
#define acc (ios::sync_with_stdio(false),cin.tie(0))
*/
#define rep(i,n) for(ll i=0;i<n;i++)
#define per(i,n) for(ll i=n-1;i>=0;i--)
#define rep1(i,n) for(ll i=1;i<=n;i++)
#define per1(i,n) for(ll i=n;i>0;i--)
#define repeat(i,start,n) for(ll i=start;i<n;i++)
#define print(a,n) for(ll i=0;i<n;i++){ cout<<a[i]<<" ";}
ll ll_max(ll a,ll b,ll c){return max(a,max(b,c));}
int int_max(int a,int b,int c){return max(a,max(b,c));}
ll ll_min(ll a,ll b,ll c){return min(a,min(b,c));}
int int_min(int a,int b,int c){return min(a,min(b,c));}
ll max(int a,ll b){ return max((ll)a,b);}
ll min(int a,ll b){ return min((ll)a,b);}
ll min(ll a,int b){ return min(a,(ll)b);}
ll max(ll a,int b){ return max(a,(ll)b);}
ll dx[]={0,0,1,-1};
ll dy[]={1,-1,0,0};
ll power(ll a,ll b){
	if(a==1)
		return 1;
	if(b==0)
		return 1;
	ll c=power(a,b/2);
	ll res=1;
	if(b%2){
		res=(c*c)%mod;
		res*=a;
		res%=mod;
	}
	else
		res=((c*c)%mod);
	return res;
}
ll modInv(ll a){return power(a,mod-2)%mod;}
ll fact[1],inv[1];
void factorial(ll n){
	fact[0]=1;
	for(ll i=1;i<=n;i++){
		fact[i]=fact[i-1]*i;
		fact[i]%=mod;
	}
}
void InvFactorial(ll n){
	inv[0]=1;
	for(ll i=1;i<=n;i++)
		inv[i]=modInv(fact[i]);
}
ll ncr(ll n,ll r){
	if(n<r||n<0||r<0)
		return 0;
	ll b=inv[n-r];
	ll c=inv[r];
	ll a=fact[n]*b;
	a%=mod;
	a*=c;
	a%=mod;
	return a;
}
//ifstream cin("b_read_on.txt"); ofstream cout("output3.txt");
//Chronology: Binary Search,Greedy,dp,dfs and similar
//Use (<<) for multiplication
//Use (>>) for division
//If memory limit exceeds in top-down , try bottom up dp
//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);
// find_by_order -> value at index
// order_of_key -> index of value
// while using (1<<i) use ((ll)1<<(ll)i)
// if global declared initialise per testcase
// in Floyd-Warshall Algo, k is outer loop
//pair is initialised as {0,0}
//value of dp array is not the same in top-down & bottom-up
// If an element was not initially in map and if asked mp[a],the element gets inserted
// Dont use unordered_map until necessary
ll n,s,l;
ll a[100001];
int dp1[100001];
ll Tree[400001],Tree1[400001];
void build_max(int node,int start,int end){
	if(start==end){
		Tree[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_max(2*node+1,start,mid);
	build_max(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree[node]=max(Tree[2*node+1],Tree[2*node+2]);
}
ll query_max(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 0;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_max(node*2+1, start, mid, l,r);
	ll p2 = query_max(node*2+2, mid+1, end , l,r);
	return max(p1,p2);
}
void build_min(int node,int start,int end){
	if(start==end){
		Tree1[node]=a[start];
		return;
	}
	int mid=((start+end)>>1);
	build_min(2*node+1,start,mid);
	build_min(2*node+2,mid+1,end);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
void update_min(int node,int start,int end,int i,ll val){
	if(start==end){
		Tree1[node]=val;
		return;
	}
	int mid=((start+end)>>1);
	if(i<=mid)
		update_min(2*node+1,start,mid,i,val);
	else
		update_min(2*node+2,mid+1,end,i,val);
	//According to the question,change from here
	Tree1[node]=min(Tree1[2*node+1],Tree1[2*node+2]);
}
ll query_min(int node,int start,int end,int l,int r){
	if(start>end||end<l||start>r)
		return 100000000000000;//0 in case of sum , high value in case of min , low value in case of max and soooo on
	if(start>=l&&end<=r)
		return(Tree1[node]);
	int mid = (start+end)/2 ;
	ll p1 = query_min(node*2+1, start, mid, l,r);
	ll p2 = query_min(node*2+2, mid+1, end , l,r);
	return min(p1,p2);
}
ll dp[100001];
void solve(int countu){
	cin>>n>>s>>l;
	rep(i,n){
		scanf("%lld",&a[i]);
		a[i]+=mod;
	}
	if(l>n){
		cout1(-1);
		return;
	}
	ll minn,maxx,j=n-2;
	build_max(0,0,n-1);
	build_min(0,0,n-1);
	for(int i=n-1;i>=0;i--){
		maxx=query_max(0,0,n-1,j+1,i);
		minn=query_min(0,0,n-1,j+1,i);
		while(j>=0){
			ll maxx1=max(maxx,a[j]);
			ll minn1=min(minn,a[j]);
			if(maxx1-minn1<=s){
				maxx=maxx1;
				minn=minn1;
				j--;
				continue;
			}
			break;
		}
		dp1[i]=max(0,j);
	}
	ll k=query_max(0,0,n-1,0,l-1)-query_min(0,0,n-1,0,l-1);
	memset(Tree1,0,sizeof(Tree1));
	repeat(i,1,l-1)
		update_min(0,0,n-1,i,inf);
	if(k<=s)
		update_min(0,0,n-1,l-1,1);
	else
		update_min(0,0,n-1,l-1,inf);
	repeat(i,l,n){
		if(dp1[i]>i-l){
			update_min(0,0,n-1,i,inf);
			continue;
		}
		ll j=query_min(0,0,n-1,dp1[i],i-l);
		j++;
		update_min(0,0,n-1,i,j);
	}
	if(query_min(0,0,n-1,n-1,n-1)>=1e12)
		cout1(-1);
	else
		cout1(query_min(0,0,n-1,n-1,n-1));
}
int main(){
	//ios_base::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);cout<<fixed;cerr.tie(NULL);cout.precision(10);
	int t=1;
	//scanf("%d",&t);
	int countu=1;
    while(t--){
    	solve(countu);
    	countu++;
    }
}


#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
using namespace std;
using namespace __gnu_pbds;
#define REP(i,j,k)     for(int i = j ; i < k ; ++i)
#define RREP(i,j,k)    for(int i = j ; i >=k ; --i)
#define A    first
#define B    second
#define pb   push_back
#define mp   make_pair
#define PII pair<int , int>
#define MEM(i,j)   memset(i , j , sizeof i)
#define ALL(i)     i.begin() , i.end()
#define DBGG(i,j)     cout << i << " " << j << endl
#define DB4(i,j,k,l)  cout << i << " " << j << " " << k << " " << l << endl
#define IOS cin.tie() , cout.sync_with_stdio(0)
#define endl "\n"
///------------------------------------------------------------
#define MAX 100900
#define INF 0x3f3f3f3f

int n , m , k;
int x[MAX] , dp[MAX];

int32_t main(){
    IOS;
    cin >> n >> m >> k;
    REP(i , 1 , n + 1) cin >> x[i];

    MEM(dp , -1) , dp[0] = 0;

    int l = 1;
    multiset<int> cc;
    REP(i , 1 , n + 1){
        // DBGG("now = " , i);
        cc.insert(x[i]);
        auto fr = cc.begin() , ba = cc.end(); ba--;
        int a = *fr , b = *ba;
        while(abs(b - x[i]) > m || abs(a - x[i]) > m){
            cc.erase(cc.find(x[l++]));
            fr = cc.begin() , ba = cc.end(); ba--;
            a = *fr , b = *ba;
        }
        if(cc.size() >= k && dp[l - 1] != -1) dp[i] = dp[l - 1] + 1;
        // DB4("dp[" , i , "] = " , dp[i]);
    }
    cout << dp[n] << endl;
    return 0;
}


#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
using namespace std;
using namespace __gnu_pbds;
#define REP(i,j,k)     for(int i = j ; i < k ; ++i)
#define RREP(i,j,k)    for(int i = j ; i >=k ; --i)
#define A    first
#define B    second
#define pb   push_back
#define mp   make_pair
#define PII pair<int , int>
#define MEM(i,j)   memset(i , j , sizeof i)
#define ALL(i)     i.begin() , i.end()
#define DBGG(i,j)     cout << i << " " << j << endl
#define DB4(i,j,k,l)  cout << i << " " << j << " " << k << " " << l << endl
#define IOS cin.tie() , cout.sync_with_stdio(0)
#define endl "\n"
///------------------------------------------------------------
#define int long long
#define MAX 100900
#define INF 0x3f3f3f3f
#define mid ((l + r) >> 1)
#define ls (now << 1)
#define rs (now << 1 | 1)

int n , m , k;
int x[MAX] , dp[MAX] , b[MAX * 4];
void update(int now , int l , int r , int k , int v){
    if(l == k && r == k) { b[now] = v; return ;}
    else if(k <= mid) update(ls , l , mid , k , v);
    else update(rs , mid + 1 , r , k , v);
    b[now] = min(b[ls] , b[rs]);
}
int query(int now , int l , int r , int ql , int qr){
    if(ql <= l && r <= qr) return b[now];
    else if(qr <= mid) return query(ls , l , mid , ql , qr);
    else if(mid + 1 <= ql) return query(rs , mid + 1 , r , ql , qr);
    else return min(query(ls , l , mid , ql , qr) , query(rs , mid + 1 , r , ql , qr));
}
int32_t main(){
    IOS;
    cin >> n >> m >> k;
    REP(i , 1 , n + 1) cin >> x[i];

    dp[0] = 0;
    REP(i , 1 , n + 1) dp[i] = 1000000000000LL;
    MEM(dp , INF) , dp[0] = 0;
    REP(i , 0 , n + 1) update(1 , 0 , n , i , dp[i]);

    int l = 1;

    multiset<int> cc;
    REP(i , 1 , n + 1){
        // DBGG("now = " , i);
        cc.insert(x[i]);
        auto fr = cc.begin() , ba = cc.end(); ba--;
        int a = *fr , b = *ba;
        while(abs(b - x[i]) > m || abs(a - x[i]) > m){
            cc.erase(cc.find(x[l++]));
            fr = cc.begin() , ba = cc.end(); ba--;
            a = *fr , b = *ba;
        }
        if(cc.size() >= k && dp[l - 1] != -1){
            int ll = l - 1 , rr = i - k;
            dp[i] = min(dp[i] , query(1 , 0 , n , ll , rr) + 1);

            update(1 , 0 , n , i , dp[i]);
        }
        // DB4("dp[" , i , "] = " , dp[i]);
    }
    if(dp[n] > n + 10) dp[n] = -1;
    cout << dp[n] << endl;
    return 0;
}


#include <bits/stdc++.h>
using namespace std;
#define sc(x)            scanf("%d",&x)
#define scc(x)           scanf("%c",&x)
#define scl(x)           scanf("%lld",&x)
#define sz(v)	     	(v.size())
#define mem(v, d)		memset(v, d, sizeof(v))
#define oo				2000000100
#define OO				4000000000000000100
#define PI 3.14159265
typedef unsigned int uint;
typedef long long ll;
//-----------------------------------------------------
const int N = 100005;
const ll MOD = 1e9 + 7;

int dX[] = {0,0,1,-1};
int dY[] = {1,-1,0,0};

//ll GCD(ll num,ll ones) { return !ones ? num : GCD(ones,num%ones); }
//ll lcm(ll a, ll b) { return (a / GCD(a, b)) * b; }
//double Len(int x,int y,int X,int Y) { return sqrt((X-x)*(X-x)+(Y-y)*(Y-y)); }
/*ll fastP(ll b,ll p)
{
    if(p==0) return 1;
    else if(p==1) return b;
    ll a = fastP(b,p/2)%MOD;
    if(p%2) return (((a*a)%MOD)*b)%MOD;
    else return (a*a)%MOD;
}*/
//----------------- ------   -------
int a[N],n,s,k,dp[N]; pair<int,int> seg[4*N];
pair<int,int> Build(int id = 1,int l=1,int r=n)
{
    if(l==r) return seg[id] = {a[l],a[l]};
    int mid = (l+r)/2;
    pair<int,int> L = Build(id*2,l,mid),R = Build(id*2+1,mid+1,r);
    return seg[id] = {max(L.first,R.first),min(L.second,R.second)};
}
pair<int,int> Get(int L,int R,int id = 1,int l=1,int r=n)
{
    if(r<L||l>R) return {-oo,oo};
    if(l>=L&&r<=R) return seg[id];
    int mid = (l+r)/2;
    pair<int,int> ll = Get(L,R,id*2,l,mid),rr = Get(L,R,id*2+1,mid+1,r);
    return {max(ll.first,rr.first),min(ll.second,rr.second)};
}
int MxDff(int l,int r)
{
    pair<int,int>tmp = Get(l,r);
    return tmp.first-tmp.second;
}
int solve()
{
    queue<int>q; int lst = 0;
    for(int i=1;i<=n;++i)
    {
        while(!q.empty()&&MxDff(q.front(),i)>s) lst = q.front(),q.pop();
        q.push(i);
        dp[i] = oo;
        if(sz(q)>=k) dp[i] = dp[lst]+1;
        while(dp[i]>=oo&&sz(q)>k) dp[i] = min(dp[lst]+1,dp[i]),lst = q.front(),q.pop();
    }
    return dp[n];
}
int main()
{
#ifndef ONLINE_JUDGE
    freopen("i.txt", "r", stdin);
    //freopen("output.txt", "w", stdout);
#endif
    sc(n); sc(s); sc(k);
    for(int i=1;i<=n;++i) sc(a[i]);
    Build();
    int ans = solve();
    if(ans>=oo) puts("-1");
    else printf("%d\n",ans);

    return 0;
}


#include "bits/stdc++.h"
using namespace std;

const int maxn = 100005;
using ll = long long;

ll a[maxn];
int prv[maxn];
pair<ll, ll> dummy = make_pair(1e18, -1e18);
int dp[maxn];

struct segtree {
	vector<pair<ll, ll>> t;
	void init(){
		t.resize(maxn << 2);
	}
	void upd(int node, int b, int e, int i, ll val){
		if(i > e || i < b)return;
		if(b == i && i == e){
			t[node] = make_pair(val, val);
			return;
		}
		int mid = (b + e) >> 1;
		upd(2*node, b, mid, i, val);
		upd(2*node + 1, mid + 1, e, i, val);
		t[node].first = min(t[2*node].first, t[2*node + 1].first);
		t[node].second = max(t[2*node].second, t[2*node + 1].second);
	}
	pair<ll, ll> query(int node, int b, int e, int i, int j){
		if(j < i)return make_pair(1e6, -1e18);
		if(i > e || j < b)return dummy;
		if(b >= i && j >= e)return t[node];
		int mid = (b + e) >> 1;
		pair<ll, ll> p1 = query(2*node, b, mid, i, j);
		pair<ll, ll> p2 = query(2*node + 1, mid + 1, e, i, j);
		return make_pair(min(p1.first, p2.first), max(p1.second, p2.second));
	}
};

int main(int argc, char const *argv[])
{
//	freopen("in.txt", "r", stdin);
	int n, l;
	ll s;
	segtree t;
	t.init();
	scanf("%d %lld %d", &n, &s, &l);
	for(int i = 1; i <= n; ++i){
		scanf("%lld", &a[i]);
		t.upd(1, 1, n, i, a[i]);
	}
	for(int i = 1; i <= n; ++i){
		int lo = 1, hi = i, ans = i;
		while(lo <= hi){
			int mid = (lo + hi) >> 1;
			pair<ll, ll> x = t.query(1, 1, n, mid, i);
			if(x.second - x.first <= s){
				ans = mid;
				hi = mid - 1;
			}else {
				lo = mid + 1;
			}
		}
		prv[i] = ans;
	}
	memset(dp, 63, sizeof dp);
	segtree t1;
	t1.init();
	for(int i = 1; i <= n; ++i){
		t1.upd(1, 0, n, i, INT_MAX);
	}
	t1.upd(1, 0, n, 0, 0);
	dp[0] = 0;
	for(int i = 1; i <= n; ++i){
		if(i - prv[i] + 1 < l)continue;
		int x = t1.query(1, 0, n, prv[i] - 1, i - l).first + 1;
		dp[i] = min(dp[i], x);
		t1.upd(1, 0, n, i, dp[i]);
	}
	if(dp[n] > n or dp[n] < 0){
		cout << "-1" << endl;
	}else {
		cout << dp[n] << endl;
	}

	return 0;
}


#include "bits/stdc++.h"
using namespace std;

const int maxn = 100005;
using ll = long long;

ll a[maxn];
int prv[maxn];
pair<ll, ll> dummy = make_pair(1e18, -1e18);
int dp[maxn];

struct segtree {
	vector<pair<ll, ll>> t;
	void init(){
		t.resize(maxn << 2);
	}
	void upd(int node, int b, int e, int i, ll val){
		if(i > e || i < b)return;
		if(b == i && i == e){
			t[node] = make_pair(val, val);
			return;
		}
		int mid = (b + e) >> 1;
		upd(2*node, b, mid, i, val);
		upd(2*node + 1, mid + 1, e, i, val);
		t[node].first = min(t[2*node].first, t[2*node + 1].first);
		t[node].second = max(t[2*node].second, t[2*node + 1].second);
	}
	pair<ll, ll> query(int node, int b, int e, int i, int j){
		if(j < i)return make_pair(1e6, -1e18);
		if(i > e || j < b)return dummy;
		if(b >= i && j >= e)return t[node];
		int mid = (b + e) >> 1;
		pair<ll, ll> p1 = query(2*node, b, mid, i, j);
		pair<ll, ll> p2 = query(2*node + 1, mid + 1, e, i, j);
		return make_pair(min(p1.first, p2.first), max(p1.second, p2.second));
	}
};

int main(int argc, char const *argv[])
{
//	freopen("in.txt", "r", stdin);
	int n, l;
	ll s;
	segtree t;
	t.init();
	scanf("%d %lld %d", &n, &s, &l);
	for(int i = 1; i <= n; ++i){
		scanf("%lld", &a[i]);
		t.upd(1, 1, n, i, a[i]);
	}
	for(int i = 1; i <= n; ++i){
		int lo = 1, hi = i, ans = i;
		while(lo <= hi){
			int mid = (lo + hi) >> 1;
			pair<ll, ll> x = t.query(1, 1, n, mid, i);
			if(x.second - x.first <= s){
				ans = mid;
				hi = mid - 1;
			}else {
				lo = mid + 1;
			}
		}
		prv[i] = ans;
	}
	memset(dp, 63, sizeof dp);
	segtree t1;
	t1.init();
	for(int i = 1; i <= n; ++i){
		t1.upd(1, 0, n, i, INT_MAX);
	}
	t1.upd(1, 0, n, 0, 0);
	dp[0] = 0;
	for(int i = 1; i <= n; ++i){
		if(i - prv[i] + 1 < l)continue;
		int x = t1.query(1, 0, n, prv[i] - 1, i - l).first + 1;
		dp[i] = min(dp[i], x);
		t1.upd(1, 0, n, i, dp[i]);
	}
	if(dp[n] > n){
		cout << "-1" << endl;
	}else {
		cout << dp[n] << endl;
	}

	return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = -0x3f3f3f3f;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 2;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        if(x == i - l + 2) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = -0x3f3f3f3f;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));
    for(int i = 1; i < l; i++)
        dp[i] = 0x3f3f3f3f;

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 2;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        if(x == i - l + 2) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 1;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr && x != i - l + 1)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;
        if(x - 1 == 0)
            dp[i] = 1;
        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 2;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        if(x == i - l + 2) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 1;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr) {
            dp[i] = query2(1, n, 1) + 1;
        }
        else
            dp[i] = 0x3f3f3f3f;
        if(x - 1 == 0)
            dp[i] = 1;
        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    if(n == 189) cout << dp[n] << endl;
    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 2;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x, qr = i;
        if(query_max(1, n, 1) - query_min(1, n, 1) > s) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 1;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x, qr = i;
        if(query_max(1, n, 1) - query_min(1, n, 1) > s) continue;

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = -0x3f3f3f3f;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));
    for(int i = 1; i < l; i++)
        dp[i] = -0x3f3f3f3f;

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 2;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        if(x == i - l + 2) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 1;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr) {
            dp[i] = query2(1, n, 1) + 1;
        }
        else
            dp[i] = 0x3f3f3f3f;
        if(x - 1 == 0)
            dp[i] = 1;
        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;

#define maxn 100010

int Max[maxn * 4], Min[maxn * 4];
int dp_Min[maxn * 4];
int a[maxn];
int dp[maxn];

int ql, qr, val;

void build(int l, int r, int o) {
    if(l == r) {
        Max[o] = Min[o] = a[l];
        return;
    }

    int mid = l + (r - l) / 2;
    build(l, mid, o * 2);
    build(mid + 1, r, o * 2 + 1);
    Max[o] = max(Max[o * 2], Max[o * 2 + 1]);
    Min[o] = min(Min[o * 2], Min[o * 2 + 1]);
}

int query_max(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Max[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0;
    if(ql <= mid) ans = max(ans, query_max(l, mid, o * 2));
    if(qr > mid) ans = max(ans, query_max(mid + 1, r, o * 2 + 1));
    return ans;
}

int query_min(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query_min(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query_min(mid + 1, r, o * 2 + 1));
    return ans;
}

int query2(int l, int r, int o) {
    if(ql <= l && qr >= r) {
        return dp_Min[o];
    }

    int mid = l + (r - l) / 2;
    int ans = 0x3f3f3f3f;
    if(ql <= mid) ans = min(ans, query2(l, mid, o * 2));
    if(qr > mid) ans = min(ans, query2(mid + 1, r, o * 2 + 1));
    return ans;
}

void update(int l, int r, int o) {
    if(l == r) {
        dp_Min[o] = val;
        return;
    }

    int mid = l + (r - l) / 2;
    if(ql <= mid) update(l, mid, o * 2);
    else update(mid + 1, r, o * 2 + 1);
    dp_Min[o] = min(dp_Min[o * 2], dp_Min[o * 2 + 1]);
}

int main() {
    int n, s, l;
    scanf("%d%d%d", &n, &s, &l);
    for(int i = 1; i <= n; i++) {
        scanf("%d", &a[i]);
    }

    build(1, n, 1);
    memset(dp_Min, 0x3f3f3f3f, sizeof(dp_Min));

    for(int i = l; i <= n; i++) {
        int x = 1, y = i - l + 1;
        while(x < y) {
            int mid = x + (y - x) / 2;
            ql = mid, qr = i;
            int val = query_max(1, n, 1) - query_min(1, n, 1);
            if(val > s) x = mid + 1;
            else y = mid;
        }

        ql = x, qr = i;
        if(query_max(1, n, 1) - query_min(1, n, 1) > s) {
            dp[i] = 0x3f3f3f3f;
            continue;
        }

        ql = x - 1, qr = i - l;
        if(ql <= qr && qr)
            dp[i] = query2(1, n, 1) + 1;
        else
            dp[i] = 0x3f3f3f3f;

        if(x - 1 == 0)
            dp[i] = 1;

        val = dp[i]; ql = i;
        update(1, n, 1);
    }

    printf("%d\n", dp[n] >= 0x3f3f3f3f ? -1 : dp[n]);
    return 0;
}


#include <bits/stdc++.h>
using namespace std;
const int N = 100005;
int seg[N * 4];

struct mq
{
    queue<int> q;
    deque<int> dq;

    void add(int x)
    {
        q.push(x);
        while (dq.size() && (dq.back() < x))
        {
            dq.pop_back();
        }
        dq.push_back(x);
    }

    void del()
    {
        if (q.front() == dq[0])
        {
            dq.pop_front();
        }
        q.pop();
    }

    int size()
    {
        return q.size();
    }

    int get()
    {
        return dq[0];
    }
};

void build(int id, int s, int e)
{
    seg[id] = 1e9;
    if (s == e)
        return;
    int mid = s + (e - s) / 2;
    build(id * 2, s, mid);
    build(id * 2 + 1, mid + 1, e);
}

void update(int id, int s, int e, int idx, int v)
{
    if (idx < s || idx > e)
        return;
    seg[id] = min(seg[id], v);
    if (s == e)
        return;
    int mid = s + (e - s) / 2;
    update(id * 2, s, mid, idx, v);
    update(id * 2 + 1, mid + 1, e, idx, v);
}

int query(int id, int s, int e, int f, int t)
{
    if (e < f || s > t)
        return 1e9;
    if (s >= f && e <= t)
        return seg[id];

    int mid = s + (e - s) / 2;
    return min(query(id * 2, s, mid, f, t), query(id * 2 + 1, mid + 1, e, f, t));
}
int arr[N];
int main()
{
   // freopen("in.txt", "rt", stdin);
    int n, d, l;
    scanf("%d %d %d", &n, &d, &l);
    for (int i = 1; i <= n; ++i)
    {
        scanf("%d", arr + i);
    }
    build(1, 0, n);
    update(1, 0, n, 0, 0);
    int i = 1;
    mq mx, mn;

    for (int j = 1; j <= n; ++j)
    {
        mx.add(arr[j]);
        mn.add(-arr[j]);
        while (mx.get() + mn.get() > d)
        {
            mx.del();
            mn.del();
            ++i;
        }
        if (j - i + 1 >= l)
        {
            int v = query(1, 0, n, i - 1, j - l);
            update(1, 0, n, j, v + 1);
        }
    }

    int v = query(1, 0, n, n, n);
    if (v <= n)
        printf("%d", v);
    else
        puts("-1");
}


#include <bits/stdc++.h>

//#include <ext/pb_ds/assoc_container.hpp> // Common file
//#include <ext/pb_ds/tree_policy.hpp> // Including tree_order_statistics_node_update

#define rep(i,n) for(i=1;i<=n;i++)
#define Rep(i,n) for(i=0;i<n;i++)
#define For(i,a,b) for(i=a;i<=b;i++)

#define pb(x) push_back(x)
#define sz(x) x.size()

#define mem(ara,val) memset(ara,val,sizeof(ara))
#define eps 1e-9

#define si(x) scanf("%d",&x)
#define sii(x,y) scanf("%d %d",&x,&y)
#define siii(x,y,z) scanf("%d %d %d",&x,&y,&z)
#define sl(x) scanf("%lld",&x)
#define sll(x,y) scanf("%lld %lld",&x,&y)
#define slll(x,y,z) scanf("%lld %lld %lld",&x,&y,&z)
#define ss(ch) scanf("%s",ch)
#define pi(x) printf("%d",x)
#define pii(x,y) printf("%d %d",x,y)
#define piii(x,y,z) printf("%d %d %d",x,y,z)
#define pl(x) printf("%lld",x)
#define pll(x,y) printf("%lld %lld",x,y)
#define plll(x,y,z) printf("%lld %lld %lld",x,y,z)
#define ps(ch) printf("%s",ch)
#define Afridi 0
#define NL printf("\n")
#define debug(x) printf("wow  %d !!\n",x)
#define Max 100005
#define INF 2000000100
//#define mod 1000000007
#define un(x) x.erase(unique( x.begin() , x.end() ), x.end())

#define FI freopen("in.txt","r",stdin)

#define D(x) cout << #x << " = " << x << endl
#define DD(x,y) cout << #x << " = " << x << "   " << #y << " = " << y << endl

typedef long long LL;
typedef unsigned long long ULL;

using namespace std;

LL bigmod(LL b,LL p,LL m)
{
    if(p == 0)return 1;
    LL my = bigmod(b,p/2,m);
    my*=my;my%=m;
    if(p & 1)my*=b,my%=m;
    return my;
}
LL setb(LL n,LL pos){return n=n | (1 << pos);}
LL resb(LL n,LL pos){return n=n & ~(1 << pos);}
bool checkb(LL n,LL pos){return (bool)(n & (1 << pos));}

struct info
{
	int mx,mn;
	info() {}
	info(int x,int y) { mn = x; mx = y; }
};
info tree[4*Max];
int ara[Max];
int n,s,d;

inline info Merge(info A,info B)
{
	info ret;
	ret.mn = A.mn;
	if(B.mn < ret.mn) ret.mn = B.mn;
	ret.mx = A.mx;
	if(B.mx > ret.mx) ret.mx = B.mx;
	return ret;
}

void init(int ind,int b,int e)
{
	if( b == e )
	{
		tree[ind] = info(ara[b],ara[b]);
		return;
	}
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	init(l,b,mid);
	init(r,mid+1,e);
	tree[ind] = Merge(tree[l],tree[r]);
}

info Q(int ind,int b,int e,int i,int j)
{
	if(i > j) return info(INF,-INF);
	if(b == i && e == j) return tree[ind];
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	return Merge( Q(l,b,mid,i,min(j,mid)) , Q(r,mid+1,e,max(mid+1,i),j) );
}

inline bool oka(int mn,int mx)
{
	if( mn < 0 || mn > INF ) return 0;
	if( mx < 0 || mx > INF ) return 0;
	return 1;
}

int Find(int l,int r)
{
	int low = 1,high = l,mid,ans = -1;
	while( low <= high )
	{
		mid = (low + high) / 2;
		info my = Q(1,1,n,mid,r);
		if( oka(my.mn,my.mx) && (my.mx - my.mn) <= s )
		{
			ans = mid;
			high = mid - 1;
		}
		else low = mid + 1;
	}
	return ans;
}

int dp[Max];
int fuck[Max];
void U(int ind,int b,int e,int i,int x)
{
	if(b == e)
	{
		fuck[ind] = x;
		return;
	}
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	if( i <= mid ) U(l,b,mid,i,x);
	else U(r,mid+1,e,i,x);
	fuck[ind] = min(fuck[l],fuck[r]);
}

int Q1(int ind,int b,int e,int i,int j)
{
	if(i > j) return INF;
	if(b == i && e == j) return fuck[ind];
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	return min( Q1(l,b,mid,i,min(j,mid)) , Q1(r,mid+1,e,max(mid+1,i),j) );
}

int solve()
{
	dp[0] = 0;
	U(1,1,n+1,1,0);
	int i;
	rep(i,n)
	{
		int r = i;
		int l = r - d + 1;
		if(l < 1) dp[i] = INF;
		else
		{
			int idx = Find(l,r);
			if( idx == -1 ) dp[i] = INF;
			else
			{
				int val = Q1(1,1,n+1,idx,l);
				dp[i] = val + 1;
			}
		}
		U(1,1,n+1,i+1,dp[i]);
		//DD(i,dp[i]);
	}
	return dp[n];
}

int main()
{
	//FI;
	int i;
    siii(n,s,d);
    rep(i,n) si(ara[i]), ara[i] += 1000000000;
    init(1,1,n);
    int ret = solve();
    if( ret > n ) ret = -1;
    pi( ret ); NL;
	return 0;
}


#include <bits/stdc++.h>

//#include <ext/pb_ds/assoc_container.hpp> // Common file
//#include <ext/pb_ds/tree_policy.hpp> // Including tree_order_statistics_node_update

#define rep(i,n) for(i=1;i<=n;i++)
#define Rep(i,n) for(i=0;i<n;i++)
#define For(i,a,b) for(i=a;i<=b;i++)

#define pb(x) push_back(x)
#define sz(x) x.size()

#define mem(ara,val) memset(ara,val,sizeof(ara))
#define eps 1e-9

#define si(x) scanf("%d",&x)
#define sii(x,y) scanf("%d %d",&x,&y)
#define siii(x,y,z) scanf("%d %d %d",&x,&y,&z)
#define sl(x) scanf("%lld",&x)
#define sll(x,y) scanf("%lld %lld",&x,&y)
#define slll(x,y,z) scanf("%lld %lld %lld",&x,&y,&z)
#define ss(ch) scanf("%s",ch)
#define pi(x) printf("%d",x)
#define pii(x,y) printf("%d %d",x,y)
#define piii(x,y,z) printf("%d %d %d",x,y,z)
#define pl(x) printf("%lld",x)
#define pll(x,y) printf("%lld %lld",x,y)
#define plll(x,y,z) printf("%lld %lld %lld",x,y,z)
#define ps(ch) printf("%s",ch)
#define Afridi 0
#define NL printf("\n")
#define debug(x) printf("wow  %d !!\n",x)
#define Max 100005
#define INF 2100100100
//#define mod 1000000007
#define un(x) x.erase(unique( x.begin() , x.end() ), x.end())

#define FI freopen("in.txt","r",stdin)

#define D(x) cout << #x << " = " << x << endl
#define DD(x,y) cout << #x << " = " << x << "   " << #y << " = " << y << endl

typedef long long LL;
typedef unsigned long long ULL;

using namespace std;

LL bigmod(LL b,LL p,LL m)
{
    if(p == 0)return 1;
    LL my = bigmod(b,p/2,m);
    my*=my;my%=m;
    if(p & 1)my*=b,my%=m;
    return my;
}
LL setb(LL n,LL pos){return n=n | (1 << pos);}
LL resb(LL n,LL pos){return n=n & ~(1 << pos);}
bool checkb(LL n,LL pos){return (bool)(n & (1 << pos));}

struct info
{
	int mx,mn;
	info() {}
	info(int x,int y) { mn = x; mx = y; }
};
info tree[4*Max];
int ara[Max];
int n,s,d;

inline info Merge(info A,info B)
{
	info ret;
	ret.mn = A.mn;
	if(B.mn < ret.mn) ret.mn = B.mn;
	ret.mx = A.mx;
	if(B.mx > ret.mx) ret.mx = B.mx;
	return ret;
}

void init(int ind,int b,int e)
{
	if( b == e )
	{
		tree[ind] = info(ara[b],ara[b]);
		return;
	}
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	init(l,b,mid);
	init(r,mid+1,e);
	tree[ind] = Merge(tree[l],tree[r]);
}

info Q(int ind,int b,int e,int i,int j)
{
	if(i > j) return info(INF,-INF);
	if(b == i && e == j) return tree[ind];
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	return Merge( Q(l,b,mid,i,min(j,mid)) , Q(r,mid+1,e,max(mid+1,i),j) );
}

int Find(int l,int r)
{
	int low = 1,high = l,mid,ans = -1;
	while( low <= high )
	{
		mid = (low + high) / 2;
		info my = Q(1,1,n,mid,r);
		assert( (my.mx - my.mn) >= 0 );
		if( (my.mx - my.mn) <= s )
		{
			ans = mid;
			high = mid - 1;
		}
		else low = mid + 1;
	}
	return ans;
}

int dp[Max];
int fuck[Max];
void U(int ind,int b,int e,int i,int x)
{
	if(b == e)
	{
		fuck[ind] = x;
		return;
	}
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	if( i <= mid ) U(l,b,mid,i,x);
	else U(r,mid+1,e,i,x);
	fuck[ind] = min(fuck[l],fuck[r]);
}

int Q1(int ind,int b,int e,int i,int j)
{
	if(i > j) return INF;
	if(b == i && e == j) return fuck[ind];
	int mid = (b + e) / 2, l = 2 * ind, r = l + 1;
	return min( Q1(l,b,mid,i,min(j,mid)) , Q1(r,mid+1,e,max(mid+1,i),j) );
}

int solve()
{
	dp[0] = 0;
	U(1,1,n+1,1,0);
	int i;
	rep(i,n)
	{
		int r = i;
		int l = r - d + 1;
		if(l < 1) dp[i] = INF;
		else
		{
			int idx = Find(l,r);
			if( idx == -1 ) dp[i] = INF;
			else
			{
				int val = Q1(1,1,n+1,idx,l);
				dp[i] = val + 1;
			}
		}
		U(1,1,n+1,i+1,dp[i]);
		//DD(i,dp[i]);
	}
	return dp[n];
}

int main()
{
	//FI;
	int i;
    siii(n,s,d);
    rep(i,n) si(ara[i]), ara[i] += 1000000000;
    rep(i,n) assert( 0 <= ara[i] && ara[i] <= 2000000000 );
    init(1,1,n);
    int ret = solve();
    if( ret > n ) ret = -1;
    pi( ret ); NL;
	return 0;
}