Mysql 如何在使用$query时保留要选择的字段的顺序->;addExpression()

Mysql 如何在使用$query时保留要选择的字段的顺序->;addExpression(),mysql,drupal-7,dynamic-queries,Mysql,Drupal 7,Dynamic Queries,我正在使用Drupal7,我必须在多个表上建立一个并集。为使工会发挥作用,必须满足以下条件: 相同数量的列 相同数据类型 相同的顺序 一些表缺少一列,因此为了弥补这一点,我只添加了如下内容:$query->addExpression(':field_1','field_1',array(':field_1'=>NULL))。因此,此时满足条件1和2,但选择中字段的顺序不同 参见下面的示例: $query_1 = db_select('table_one', 't1'); $query_1

我正在使用Drupal7,我必须在多个表上建立一个并集。为使工会发挥作用,必须满足以下条件:

  • 相同数量的列
  • 相同数据类型
  • 相同的顺序
  • 一些表缺少一列,因此为了弥补这一点,我只添加了如下内容:
    $query->addExpression(':field_1','field_1',array(':field_1'=>NULL))。因此,此时满足条件1和2,但选择中字段的顺序不同

    参见下面的示例:

      $query_1 = db_select('table_one', 't1');
      $query_1->fields('t1', array('field_1', 'field_2'));
    
      $query_2 = db_select('table_two', 't2');
      if (true) {
        $query_2->fields('t2', array('field_1'));
      } else {
        $query_2->addExpression(':field_1', 'field_1', array(':field_1' => NULL));
      }
      $query_2->fields('t2', array('field_2'));        
    
      $query_3 = db_select('table_three', 't3');
      if (false) {
        $query_3->fields('t3', array('field_1'));
      } else {
        $query_3->addExpression(':field_1', 'field_1', array(':field_1' => NULL));
      }
      $query_3->fields('t3', array('field_2'));
    
    结果是:

    // dpq($query_1);
    SELECT t1.field_1 AS field_1, t1.field_2 AS field_2
    FROM {table_one} t1
    
    // dpq($query_2);
    SELECT t2.field_1 AS field_1, t2.field_2 AS field_2
    FROM {table_two} t2
    
    // dpq($query_3);
    SELECT t3.field_2 AS field_2, '' AS field_1
    FROM {table_three} t3
    
    // dpq($query_1->union($query_2)->union($query_3));
    SELECT t1.field_1 AS field_1, t1.field_2 AS field_2
    FROM {table_one} t1 
    UNION SELECT t2.field_1 AS field_1, t2.field_2 AS field_2
    FROM {table_two} t2 
    UNION SELECT t3.field_2 AS field_2, '' AS field_1
    FROM {table_three} t3
    

    似乎使用
    $query->addExpression
    并不能保证字段的位置是您期望的位置。查看第三个查询的转储,其中使用了
    addExpression
    。关于如何解决这个问题,你有什么想法吗?

    这是我找到的唯一能维持秩序的方法。使用表达式,即使该字段是否存在。这样,订单就是您所期望的:

    if (TRUE) {
      // To keep the order of the fields we have to use this hacky way.
      // Use a function that will not modify the string
      $query->addExpression("IFNULL(table_name.field_name, '')", 'field_name_alias');
    } else {
      $query->addExpression(':field', 'field_name_alias', array(':field' => NULL));
    }
    

    我想添加一个简化的示例。用于保持字段的顺序,而不是

    $query->addField('n', 'uid', 'node_uid');
    
    你可以写

    $query->addExpression('n.uid', 'node_uid');