code: def _separate_sq(p):
      """
      helper function for ``_minimal_polynomial_sq``
  
      It selects a rational ``g`` such that the polynomial ``p``
      consists of a sum of terms whose surds squared have gcd equal to ``g``
      and a sum of terms with surds squared prime with ``g``;
      then it takes the field norm to eliminate ``sqrt(g)``
  
      See simplify.simplify.split_surds and polytools.sqf_norm.
  
      Examples
      ========
  
      >>> from sympy import sqrt
      >>> from sympy.abc import x
      >>> from sympy.polys.numberfields.minpoly import _separate_sq
      >>> p= -x + sqrt(2) + sqrt(3) + sqrt(7)
      >>> p = _separate_sq(p); p
      -x**2 + 2*sqrt(3)*x + 2*sqrt(7)*x - 2*sqrt(21) - 8
      >>> p = _separate_sq(p); p
      -x**4 + 4*sqrt(7)*x**3 - 32*x**2 + 8*sqrt(7)*x + 20
      >>> p = _separate_sq(p); p
      -x**8 + 48*x**6 - 536*x**4 + 1728*x**2 - 400
  
      """
  
      def is_sqrt(expr):
          return expr.is_Pow and expr.exp is S.Half
  
      # p = c1*sqrt(q1) + ... + cn*sqrt(qn) -> a = [(c1, q1), .., (cn, qn)]
      a = []
      for y in p.args:
          if not y.is_Mul:
              if is_sqrt(y):
                  a.append((S.One, y**2))
              elif y.is_Atom:
                  a.append((y, S.One))
              elif y.is_Pow and y.exp.is_integer:
                  a.append((y, S.One))
              else:
                  raise NotImplementedError
          else:
              T, F = sift(y.args, is_sqrt, binary=True)
              a.append((Mul(*F), Mul(*T) ** 2))
      a.sort(key=lambda z: z[1])
      if a[-1][1] is S.One:
          # there are no surds
          return p
      surds = [z for y, z in a]
      for i in range(len(surds)):
          if surds[i] != 1:
              break
      from sympy.simplify.radsimp import _split_gcd
  
      g, b1, b2 = _split_gcd(*surds[i:])
      a1 = []
      a2 = []
      for y, z in a:
          if z in b1:
              a1.append(y * z**S.Half)
          else:
              a2.append(y * z**S.Half)
      p1 = Add(*a1)
      p2 = Add(*a2)
      p = _mexpand(p1**2) - _mexpand(p2**2)
      return p
  
imports: from functools import reduce
  from sympy.core.add import Add
  from sympy.core.exprtools import Factors
  from sympy.core.function import expand_mul, expand_multinomial, _mexpand
  from sympy.core.mul import Mul
  from sympy.core.numbers import I, Rational, pi, _illegal
  from sympy.core.singleton import S
  from sympy.core.symbol import Dummy
  from sympy.core.sympify import sympify
  from sympy.core.traversal import preorder_traversal
  from sympy.functions.elementary.exponential import exp
  from sympy.functions.elementary.miscellaneous import sqrt, cbrt
  from sympy.functions.elementary.trigonometric import cos, sin, tan
  from sympy.ntheory.factor_ import divisors
  from sympy.utilities.iterables import subsets
  from sympy.polys.domains import ZZ, QQ, FractionField
  from sympy.polys.orthopolys import dup_chebyshevt
  from sympy.polys.polyerrors import NotAlgebraic, GeneratorsError
  from sympy.polys.polytools import Poly, PurePoly, invert, factor_list, groebner, resultant, degree, poly_from_expr, parallel_poly_from_expr, lcm
  from sympy.polys.polyutils import dict_from_expr, expr_from_dict
  from sympy.polys.ring_series import rs_compose_add
  from sympy.polys.rings import ring
  from sympy.polys.rootoftools import CRootOf
  from sympy.polys.specialpolys import cyclotomic_poly
  from sympy.utilities import numbered_symbols, public, sift
label_desc: Use image node_id 3 for calling a global function with example usage: _separate_sq(p) and returns: p, unknown, p