0

I'm looking for query that selects different column name, dynamically, by variable.

Suppose I have that contains my "dynamic columns" I'd like to select , something like this:

SELECT `ObjectID`,`ObjectLabel` FROM `modules_forms_objects`
+----------+---------------+
| ObjectID | ObjectLabel   |
+----------+---------------+
|       71 | Join Date     |
|       72 | Active        |
+----------+---------------+

Now, I've got one more table, which it's columns called by the "ObjectID" as above. Here:

SELECT `data_id`,`71`,`72` FROM `7`
+---------+---------------------+------+
| data_id | 71                  | 72   |
+---------+---------------------+------+
|       1 | 0000-00-00 00:00:00 | NULL |
+---------+---------------------+------+

I want to join a "Value" column to the first table, and this'll contain the Value from the match Column in the second table. (for example: for ObjectID #72 the value will be NULL).

Ultimately, I want my result to be like this:

+----------+---------------+--------------------+
| ObjectID | ObjectLabel   |       Value    |
+----------+---------------+--------------------+
|       71 | Join Date     |0000-00-00 00:00:00 |
|       72 | Active        |        NULL    |
+----------+---------------+--------------------+

When I used traditional "JOIN" I got the all columns for each row, and it seems kind of heavy.

Any ideas? Thanks a lot!

1
  • you are having lots and lots of coulmns, don't you? Commented Aug 25, 2013 at 18:50

3 Answers 3

1

The base static query might look like this

SELECT m.ObjectID, m.ObjectLabel, q.Value
  FROM modules_forms_objects m LEFT JOIN
(
  SELECT objectid,
         CASE objectid 
            WHEN 71 THEN `71`
            WHEN 72 THEN `72`
         END value
    FROM `7` t CROSS JOIN
  (
    SELECT 71 objectid UNION ALL
    SELECT 72 
  ) c
) q 
    ON m.objectid = q.objectid

The idea is to first unpivot your 7 table and then outer join it with modules_forms_objects

Output:

| OBJECTID | OBJECTLABEL |               VALUE |
-----------|-------------|---------------------|
|       71 |   Join Date | 0000-00-00 00:00:00 |
|       72 |      Active |              (null) |

Here is SQLFiddle demo

If you don't have dozens and dozens of columns in 7 table I'd recommend to stick with the static query.


Now same thing with dynamic SQL

SET @sql = NULL, @sql1 = NULL, @sql2 = NULL;

SELECT GROUP_CONCAT(
           CONCAT('WHEN ''',  column_name, ''' THEN `', column_name, '`')
       SEPARATOR ' ')
  INTO @sql1
  FROM INFORMATION_SCHEMA.COLUMNS
 WHERE table_schema = SCHEMA()
   AND table_name = '7'
   AND column_name LIKE '7%'
 GROUP BY table_name;

SELECT GROUP_CONCAT(
           CONCAT('SELECT ''',  column_name, ''' objectid' )
       SEPARATOR ' UNION ALL ')
  INTO @sql2
  FROM INFORMATION_SCHEMA.COLUMNS
 WHERE table_schema = SCHEMA()
   AND table_name = '7'
   AND column_name LIKE '7%'
 GROUP BY table_name;

SET @sql = CONCAT(
'SELECT m.ObjectID, m.ObjectLabel, q.Value
  FROM modules_forms_objects m LEFT JOIN
(
  SELECT objectid,
         CASE objectid ', @sql1, ' END value 
    FROM `7` t CROSS JOIN
  (', @sql2, '
  ) c
) q
    ON m.objectid = q.objectid');

PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;

Here is SQLFiddle demo

Sign up to request clarification or add additional context in comments.

3 Comments

Thanks. Do you know if there is any way to this dynamic? if I'll do so, i'll have to use php to generate the CASE syntax, and i'm trying to avoid this.
@Dan You're welcome. See updated answer. I just showed how to do that using dynamic SQL. You can wrap it a stored procedure to simplify things on client (php) side.
@Dan If you feel like it was what you were looking for please, consider to accept the answer.
1

USE SHOW COLUMNS FROM tab_name and use FIELD property to get the corresponding column.

Comments

0

This would give all column names in a particular table

SELECT 
        GROUP_CONCAT(COLUMN_NAME)
FROM 
        INFORMATION_SCHEMA.COLUMNS
WHERE 
        table_name = 'mytable'

1 Comment

Small improvement: SELECT GROUP_CONCAT(DISTINCT COLUMN_NAME ORDER BY COLUMN_NAME) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_name = 'myTable'

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.