import std.stdio, std.conv, std.array, std.string, std.algorithm, std.container, std.range, core.stdc.stdlib, std.math, std.typecons;
T[][] combinations(T)(T[] s, in int m) {   if (!m) return [[]];   if (s.empty) return [];   return s[1 .. $].combinations(m - 1).map!(x => s[0] ~ x).array ~ s[1 .. $].combinations(m); }


class PanaNumber {
  static int SIZE;
  static int max() {
    int max_number;
    int dec = 1;
    foreach(i; 0..SIZE-1) {
      max_number += dec * (SIZE - i - 1);
      dec *= 10;
    }
    return max_number;
  }

  int number;
  this(int i) {
    number = i;
  }

  bool isEquival(int other) {
    foreach(dec1; 0..SIZE-1) {
      const div1 = 10.pow(dec1);
      foreach(dec2; dec1+1..SIZE) {
        const div2 = 10.pow(dec2);
        const si = (number / div1) % 10;
        const sj = (number / div2) % 10;
        const ti = (other / div1) % 10;
        const tj = (other / div2) % 10;
        debug writeln([number, other, dec1, dec2, div1, div2]);
        debug writeln([si, sj, ti, tj, si == sj, ti == tj]);
        if ((si == sj && ti != tj) || (si != sj && ti == tj)) {
          return false;
        }
      }
    }
    return true;
  }

  override string toString() {
    auto chars = new char[SIZE];
    int num = number;
    foreach(i; 0..SIZE) {
      chars[SIZE - i - 1] = cast(char)('a' + (num % 10));
      num /= 10;
    }

    return cast(string)chars;
  }
}

void main() {
  const N = readln.chomp.to!int;
  PanaNumber.SIZE = N;
  
  PanaNumber[] standardPanaNumbers;
  void solve() {
    foreach(i; 0..PanaNumber.max+1) {
      if (standardPanaNumbers.any!(p => p.isEquival(i))) continue;

      standardPanaNumbers ~= new PanaNumber(i);
    }

    standardPanaNumbers.to!(string[]).joiner("\n").writeln;
  }

  solve();
}
