description: Given a positive integer n. Find three distinct positive integers a, b, c such that a + b + c = n and \operatorname{gcd}(a, b) = c, where \operatorname{gcd}(x, y) denotes the [greatest common divisor (GCD)](https://en.wikipedia.org/wiki/Greatest_common_divisor) of integers x and y.
  
  Input
  
  The input consists of multiple test cases. The first line contains a single integer t (1 ≤ t ≤ 10^5) — the number of test cases. Description of the test cases follows.
  
  The first and only line of each test case contains a single integer n (10 ≤ n ≤ 10^9).
  
  Output
  
  For each test case, output three distinct positive integers a, b, c satisfying the requirements. If there are multiple solutions, you can print any. We can show that an answer always exists.
  
  Example
  
  Input
  
  
  6
  18
  63
  73
  91
  438
  122690412
  
  
  Output
  
  
  6 9 3
  21 39 3
  29 43 1
  49 35 7
  146 219 73
  28622 122661788 2
  
  Note
  
  In the first test case, 6 + 9 + 3 = 18 and \operatorname{gcd}(6, 9) = 3.
  
  In the second test case, 21 + 39 + 3 = 63 and \operatorname{gcd}(21, 39) = 3.
  
  In the third test case, 29 + 43 + 1 = 73 and \operatorname{gcd}(29, 43) = 1.
solution: import java.io.*;
  import java.util.*;
  
  public class Solution2 {
      static FastScanner fs;
      static PrintWriter pw;
      public static void main(String[] args) {
          fs = new FastScanner();
          pw = new PrintWriter(System.out);
          precomp();
          int t = fs.nextInt();
          while (t-- > 0)
              solve();
          pw.close();
      }
      public static void precomp() {
  
      }
      static class pair {
          int lo, hi;
          pair (int x, int y) {lo=x; hi=y;}
          public int hashCode() {
              return lo*1000+hi;
          }
          public boolean equals(Object o) {
              pair po = (pair) o;
              return lo==po.lo && hi==po.hi;
          }
      }
      public static void solve() {
          int a = fs.nextInt();
          if (a%2==0) {
              System.out.println(a-3+" "+2+" "+1);
          }
          else if (a%4==3){
              System.out.println(a/2+2+" "+(a/2-2)+" "+1);
          }
          else {
              System.out.println((a/2-1)+" "+(a/2+1)+" "+1);
          }
      }
      static long pow(long b, long exp, long mod) {
          long ret = 1;
          while (exp > 0) {
              if ((exp & 1) > 0)
                  ret = (ret * b) % mod;
              b = (b * b) % mod;
              exp >>= 1;
          }
          return ret;
      }
  
      static int nCrmod(int n, int r, int mod) {
          if (r > n)
              return 0;
          if (n - r > r)
              r = n - r;
          int[] SPF = new int[n + 1];
          for (int i = 1; i <= n; i++)
              SPF[i] = i;
          for (int i = 4; i <= n; i += 2)
              SPF[i] = 2;
          for (int i = 3; i * i < n + 1; i += 2) {
              if (SPF[i] == i) {
                  for (int j = i * i; j < n + 1; j += i)
                      if (SPF[j] == j) {
                          SPF[j] = i;
                      }
              }
          }
          Map<Integer, Integer> prime_pow = new HashMap<>();
          for (int i = r + 1; i < n + 1; i++) {
              int t = i;
              while (t > 1) {
                  prime_pow.put(SPF[t],
                          prime_pow.getOrDefault(SPF[t], 0) + 1);
                  t /= SPF[t];
              }
          }
          for (int i = 1; i < n - r + 1; i++) {
              int t = i;
              while (t > 1) {
                  prime_pow.put(SPF[t], prime_pow.get(SPF[t]) - 1);
                  t /= SPF[t];
              }
          }
          long ans = 1;
          for (int i : prime_pow.keySet())
              ans = (ans * pow(i, prime_pow.get(i), mod)) % mod;
          return (int) ans;
      }
  
      //    static int k;
  //    static int par(int curr) {
  //        return (1<<k)-1-(((1<<k)-1-curr)/2);
  //    }
  //    static int left(int curr) {
  //        return (1<<k)-1-(2*((1<<k)-1-curr)+1);
  //    }
  //    static int right(int curr) {
  //        return (1<<k)-1-(2*((1<<k)-1-curr));
  //    }
      static int gcd(int a, int b) {
          if (a == 0) return b;
          return gcd(b % a, a);
      }
  
      static void ruffleSort(int[] a) {
          int n = a.length;//shuffle, then sort
          for (int i = 0; i < n; i++) {
              int oi = random.nextInt(n), temp = a[oi];
              a[oi] = a[i];
              a[i] = temp;
          }
          Arrays.sort(a);
      }
  
      static final Random random = new Random();
  
      static class FastScanner {
          BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
          StringTokenizer st = new StringTokenizer("");
  
          String next() {
              while (!st.hasMoreTokens())
                  try {
                      st = new StringTokenizer(br.readLine());
                  } catch (IOException e) {
                      e.printStackTrace();
                  }
              return st.nextToken();
          }
  
          int nextInt() {
              return Integer.parseInt(next());
          }
  
          int[] readArray(int n) {
              int[] a = new int[n];
              for (int i = 0; i < n; i++) a[i] = nextInt();
              return a;
          }
  
          long nextLong() {
              return Long.parseLong(next());
          }
      }
  
      static int[] reverse(int[] a) {
          int n = a.length;
          int[] res = new int[n];
          for (int i = 0; i < n; i++) res[i] = a[n - 1 - i];
          return res;
      }
      static class Node {
          int sum;
          int min;
          //Here We store the value that will be propagated lazily
          Integer pendingVal = null;
          int from;
          int to;
  
          int size() {
              return to - from + 1;
          }
  
      }
      static class SegmentTree {
  
          private Node[] heap;
          private int[] array;
          private int size;
  
          /**
           * Time-Complexity:  O(n*log(n))
           *
           * @param array the Initialization array
           */
          public SegmentTree(int[] array) {
              this.array = Arrays.copyOf(array, array.length);
              //The max size of this array is about 2 * 2 ^ log2(n) + 1
              size = (int) (2 * Math.pow(2.0, Math.floor((Math.log((double) array.length) / Math.log(2.0)) + 1)));
              heap = new Node[size];
              build(1, 0, array.length);
          }
  
  
          public int size() {
              return array.length;
          }
  
          //Initialize the Nodes of the Segment tree
          private void build(int v, int from, int size) {
              heap[v] = new Node();
              heap[v].from = from;
              heap[v].to = from + size - 1;
  
              if (size == 1) {
                  heap[v].sum = array[from];
                  heap[v].min = array[from];
              } else {
                  //Build childs
                  build(2 * v, from, size / 2);
                  build(2 * v + 1, from + size / 2, size - size / 2);
  
                  heap[v].sum = heap[2 * v].sum + heap[2 * v + 1].sum;
                  //min = min of the children
                  heap[v].min = Math.min(heap[2 * v].min, heap[2 * v + 1].min);
              }
          }
  
          /**
           * Range Sum Query
           *
           * Time-Complexity: O(log(n))
           *
           * @param  from from index
           * @param  to to index
           * @return sum
           */
          public int rsq(int from, int to) {
              return rsq(1, from, to);
          }
  
          private int rsq(int v, int from, int to) {
              Node n = heap[v];
  
              //If you did a range update that contained this node, you can infer the Sum without going down the tree
              if (n.pendingVal != null && contains(n.from, n.to, from, to)) {
                  return (to - from + 1) * n.pendingVal;
              }
  
              if (contains(from, to, n.from, n.to)) {
                  return heap[v].sum;
              }
  
              if (intersects(from, to, n.from, n.to)) {
                  propagate(v);
                  int leftSum = rsq(2 * v, from, to);
                  int rightSum = rsq(2 * v + 1, from, to);
  
                  return leftSum + rightSum;
              }
  
              return 0;
          }
  
          /**
           * Range Min Query
           *
           * Time-Complexity: O(log(n))
           *
           * @param  from from index
           * @param  to to index
           * @return min
           */
          public int rMinQ(int from, int to) {
              return rMinQ(1, from, to);
          }
  
          private int rMinQ(int v, int from, int to) {
              Node n = heap[v];
  
  
              //If you did a range update that contained this node, you can infer the Min value without going down the tree
              if (n.pendingVal != null && contains(n.from, n.to, from, to)) {
                  return n.pendingVal;
              }
  
              if (contains(from, to, n.from, n.to)) {
                  return heap[v].min;
              }
  
              if (intersects(from, to, n.from, n.to)) {
                  propagate(v);
                  int leftMin = rMinQ(2 * v, from, to);
                  int rightMin = rMinQ(2 * v + 1, from, to);
  
                  return Math.min(leftMin, rightMin);
              }
  
              return Integer.MAX_VALUE;
          }
  
  
          /**
           * Range Update Operation.
           * With this operation you can update either one position or a range of positions with a given number.
           * The update operations will update the less it can to update the whole range (Lazy Propagation).
           * The values will be propagated lazily from top to bottom of the segment tree.
           * This behavior is really useful for updates on portions of the array
           * <p>
           * Time-Complexity: O(log(n))
           *
           * @param from  from index
           * @param to    to index
           * @param value value
           */
          public void update(int from, int to, int value) {
              update(1, from, to, value);
          }
  
          private void update(int v, int from, int to, int value) {
  
              //The Node of the heap tree represents a range of the array with bounds: [n.from, n.to]
              Node n = heap[v];
  
              /**
               * If the updating-range contains the portion of the current Node  We lazily update it.
               * This means We do NOT update each position of the vector, but update only some temporal
               * values into the Node; such values into the Node will be propagated down to its children only when they need to.
               */
              if (contains(from, to, n.from, n.to)) {
                  change(n, value);
              }
  
              if (n.size() == 1) return;
  
              if (intersects(from, to, n.from, n.to)) {
                  /**
                   * Before keeping going down to the tree We need to propagate the
                   * the values that have been temporally/lazily saved into this Node to its children
                   * So that when We visit them the values  are properly updated
                   */
                  propagate(v);
  
                  update(2 * v, from, to, value);
                  update(2 * v + 1, from, to, value);
  
                  n.sum = heap[2 * v].sum + heap[2 * v + 1].sum;
                  n.min = Math.min(heap[2 * v].min, heap[2 * v + 1].min);
              }
          }
  
          //Propagate temporal values to children
          private void propagate(int v) {
              Node n = heap[v];
  
              if (n.pendingVal != null) {
                  change(heap[2 * v], n.pendingVal);
                  change(heap[2 * v + 1], n.pendingVal);
                  n.pendingVal = null; //unset the pending propagation value
              }
          }
  
          //Save the temporal values that will be propagated lazily
          private void change(Node n, int value) {
              n.pendingVal = value;
              n.sum = n.size() * value;
              n.min = value;
              array[n.from] = value;
  
          }
  
          //Test if the range1 contains range2
          private boolean contains(int from1, int to1, int from2, int to2) {
              return from2 >= from1 && to2 <= to1;
          }
          //check inclusive intersection, test if range1[from1, to1] intersects range2[from2, to2]
          private boolean intersects(int from1, int to1, int from2, int to2) {
              return from1 <= from2 && to1 >= from2   //  (.[..)..] or (.[...]..)
                      || from1 >= from2 && from1 <= to2; // [.(..]..) or [..(..)..
          }
      }
      public static class DisjointSets {
          int[] parents;  // 0-indexed
          int[] sizes;
          public DisjointSets(int size) {
              sizes = new int[size];
              parents = new int[size];
              Arrays.fill(sizes, 1);
              Arrays.fill(parents, -1);
          }
  
          // finds the "representative" node in a's component
          public int find(int x) {
              return parents[x] == -1 ? x : (parents[x] = find(parents[x]));
          }
  
          // returns whether the merge changed connectivity
          public boolean union(int x, int y) {
              int xRoot = find(x);
              int yRoot = find(y);
              if (xRoot == yRoot) {
                  return false;
              }
              if (sizes[xRoot] < sizes[yRoot]) {
                  parents[xRoot] = yRoot;
                  sizes[yRoot] += sizes[xRoot];
              } else {
                  parents[yRoot] = xRoot;
                  sizes[xRoot] += sizes[yRoot];
              }
              return true;
          }
  
          // returns whether two nodes are in the same connected component
          public boolean connected(int x, int y) {
              return find(x) == find(y);
          }
      }
  
  }