#include <bits/stdc++.h>
using namespace std;
#define rep(i, n) for (int i = 0; i < (int)(n); i++)
#define _GLIBCXX_DEBUG
typedef long long int ll;
typedef long double ld;

const int inf = 1e8;
const ll llinf = 1e18;
const double PI = acos(-1);
#define yes "Yes"
#define no "No"
#define all(n) n.begin(), n.end()

template <class T>
void chmin(T &a, T b) {
  if (a > b) a = b;
}
template <class T>
void chmax(T &a, T b) {
  if (a < b) a = b;
}

struct UnionFind {
  vector<int> par, siz;
  UnionFind(int n) : par(n, -1), siz(n, 1) {}
  int root(int x) {
    if (par[x] == -1) return x;
    return par[x] = root(par[x]);
  }
  bool isSame(int x, int y) { return root(x) == root(y); }
  bool unite(int x, int y) {
    x = root(x), y = root(y);
    if (x == y) return false;
    if (siz[x] < siz[y]) swap(x, y);
    par[y] = x;
    siz[x] += siz[y];
    return true;
  }
  int size(int x) { return siz[root(x)]; }
};

using Graph = vector<vector<int>>;
vector<int> visited(false);

const int dx[4] = {1, 0, -1, 0};
const int dy[4] = {0, 1, 0, -1};
// const int dx[8] = {-1, 0, 1, -1, 1, -1, 0, 1};
// const int dy[8] = {-1, -1, -1, 0, 0, 1, 1, 1};

void dfs(const Graph &G, int v) {
  visited[v] = true;
  for (auto next : G[v]) {
    if (visited[next]) continue;
    dfs(G, next);
  }
}

bool isPrime(ll n) {
  if (n < 2) return false;
  for (ll i = 2; i * i <= n; ++i)
    if (n % i == 0) return false;
  return true;
}

// 最大公約数
ll gcd(ll a, ll b) { return b ? gcd(b, a % b) : a; }

// 最小公倍数
ll lcm(ll a, ll b) { return abs(a) / gcd(a, b) * abs(b); }

ll gcd2(const vector<ll> &v) {
  ll val = v[0];
  for (ll i = 1; i < v.size(); ++i) val = gcd(val, v[i]);
  return val;
}

ll lcm2(const vector<ll> &v) {
  ll val = v[0];
  for (ll i = 1; i < v.size(); ++i) val = lcm(val, v[i]);
  return val;
}

vector<ll> divisors(ll n) {
  vector<ll> a;
  for (ll i = 1; i * i <= n; i++) {
    if (n % i == 0) {
      a.push_back(i);
      if (n / i != i) a.push_back(n / i);
    }
  }
  sort(a.begin(), a.end());
  return a;
}

// pairを要素に持つvectorをsecondを基準にソートする比較関数
bool comp(pair<ll, ll> a, pair<ll, ll> b) { return a.second < b.second; }

vector<int> eratosthenes(int n) {
  vector<bool> is_prime(n + 1, true);
  vector<int> p;
  for (int i = 2; i <= n; ++i) {
    if (is_prime[i]) {
      for (int j = i * 2; j <= n; j += i) {
        is_prime[j] = false;
      }
      p.push_back(i);
    }
  }
  return p;
}

int main() {
  double n, d, h;
  cin >> n >> d >> h;
  double ans = 0;

  rep(i, n) {
    double dn, hn;
    cin >> dn >> hn;
    double a = (h - hn) / (d - dn);
    double b = h - a * d;
    ans = max(ans, b);
  }

    cout << fixed << setprecision(9) << ans << endl;
}

#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
using namespace __gnu_pbds;
using namespace std;
using ll = long long int;
using iPair = pair<int,int>;
using lPair = pair<ll, ll>;
using ivector = vector<int>;
using lvector = vector<ll>;
using istack = stack<int>;
using iqueue = queue<int>;
using ivv = vector<vector<int>>;
using lvv = vector<vector<ll>>;
const int INF = 0x3f3f3f3f;
const ll LINF = 0x3f3f3f3f3f3f3f3f;
vector<iPair> dir = {{1,0}, {-1,0}, {0,1}, {0,-1}};
#define dump(x) cout << #x << " = " << (x) << endl
#define ALL(x) begin(x),end(x)
#define rep(i,s,e) for(ll i=(s); i<(ll)(e); ++i)
#define repRev(i,s,e) for(ll i=(e-1); i>=(ll)(s); --i)
#define range(i,s,n) for(ll i=(s), i_stop=(s)+(n); i<i_stop; ++i)
#define rangeRev(i,s,n) for(ll i=(s), i_stop=(s)-(n); i>i_stop; --i)
#define foreach(x,container) for(auto &&x:container)
bool chmax(ll& a, ll b) {if(a<b) {a=b;return true;} return false;}
bool chmin(ll& a, ll b) {if(a>b) {a=b;return true;} return false;}
template<typename T> void printArr(vector<T> &arr){
    for(auto &&x:arr) {cout << x << " ";} cout << endl;
}


/*


## 關鍵詞：
二分，二維前綴和，中值

## 題意：
給定長寬爲N的正方形，求所有K*K的正方形區域中中值的最小值。
1 <= K <= N <= 800。
中值定義: K*K方塊中，第 (K*K/2)+1 大的數值。


## 思路：
題解：https://atcoder.jp/contests/abc203/editorial/1955
將問題轉化爲求「對於任意X，判斷是否存在一個K*K區域使得該區域的中值小於等於X」。
然後二分去尋找滿足條件的最小X。
「存在一個K*K區域使得該區域的中值小於等於X」
等價於
「存在一個K*K區域，其中大於X的方塊數量小於(K*K/2)+1」，證明很簡單。
判斷某個X是否滿足條件時，花費O(N^2)生成前綴和，然後可以在O(1)判斷K*K中大於X的方塊數量。
總的復雜度是O(max(A_i)N^2)

## 雜多：


*/

ll n,k;
ll A[810][810];
ll s[810][810];

bool check(ll x) {
    range(i, 0, n) range(j, 0, n) {
        s[i+1][j+1] = s[i+1][j] + s[i][j+1] - s[i][j];
        if(A[i][j] > x) ++s[i+1][j+1];
    }

    ll thres = k*k/2+1;
    for(int i=0; i+k<=n; ++i) for(int j=0; j+k<=n; ++j) {
        ll cnt = s[i+k][j+k];
        cnt -= s[i+k][j] + s[i][j+k];
        cnt += s[i][j];
        if(cnt < thres) return true;
    }
    return false;
}

void solve(){
    cin>>n>>k;
    range(i, 0, n) range(j, 0, n) cin>>A[i][j];
    range(i, 0, k) {
        s[i][0] = 0;
        s[0][i] = 0;
    }
    
    ll l = 0, r = 1000000001;
    while(l<r) {
        ll mid = l + (r-l) / 2;
        if(!check(mid)) l = mid+1;
        else r = mid;
    }
    cout << l << endl;
}

int main(){
    ios::sync_with_stdio(false);
    cin.tie(0);
    solve();
    return 0;
}

    
    