#include <bits/stdc++.h>
class Problem {
 public:
  void init();
  void solve();

 private:
  bool m_isLoopFound;
  std::vector<std::vector<int> > m_graph;
  std::vector<int> m_from;
  std::vector<int> m_dist;
  std::vector<bool> m_used;
  std::vector<bool> m_loop;
  void m_dfs(int cur);
  void m_dfs2(int cur);
};
int main() {
  Problem p;
  p.init();
  p.solve();
  return 0;
}
void Problem::init() {
  int n;
  std::cin >> n;
  m_isLoopFound = false;
  m_graph.resize(n);
  m_from.resize(n, -1);
  m_dist.resize(n, 0);
  m_used.resize(n, false);
  m_loop.resize(n, false);
  for (int i = 0; i < n; ++i) {
    int x;
    int y;
    std::cin >> x >> y;
    --x;
    --y;
    m_graph[x].push_back(y);
    m_graph[y].push_back(x);
  }
}
void Problem::solve() {
  m_dfs(0);
  for (int i = 0; i < m_graph.size(); ++i) std::cout << m_dist[i] << " ";
  std::cout << std::endl;
}
void Problem::m_dfs(int cur) {
  m_used[cur] = true;
  for (int i = 0; i < m_graph[cur].size() && !m_isLoopFound; ++i) {
    int to = m_graph[cur][i];
    if (to != m_from[cur]) {
      m_from[to] = cur;
      if (m_used[to]) {
        int pos = to;
        do {
          m_loop[pos] = true;
          pos = m_from[pos];
        } while (pos != -1 && pos != to);
        m_from.assign(m_graph.size(), -1);
        m_used.assign(m_graph.size(), false);
        m_dfs2(to);
        m_isLoopFound = true;
        break;
      }
      m_dfs(to);
    }
  }
}
void Problem::m_dfs2(int cur) {
  m_used[cur] = true;
  if (m_loop[cur])
    m_dist[cur] = 0;
  else
    m_dist[cur] = m_dist[m_from[cur]] + 1;
  for (int i = 0; i < m_graph[cur].size(); ++i) {
    int to = m_graph[cur][i];
    if (!m_used[to]) {
      m_from[to] = cur;
      m_dfs2(to);
    }
  }
}
