Як я можу імітувати масив змінної в MySQL?


91

Це здається , що MySQL не має масив змінних. Що я повинен використовувати замість цього?


Здається, пропонуються дві альтернативи: скалярний набір типу та тимчасові таблиці . Питання, на яке я зв’язав, пропонує перше. Але чи є гарною практикою використовувати їх замість змінних масиву? Як варіант, якщо я йду з наборами, чому б відповідала ідіома на основі набору foreach?

Відповіді:


78

Ну, я використовую тимчасові таблиці замість змінних масиву. Не найкраще рішення, але воно працює.

Зверніть увагу, що вам не потрібно формально визначати їх поля, просто створіть їх за допомогою SELECT:

DROP TEMPORARY TABLE IF EXISTS my_temp_table;
CREATE TEMPORARY TABLE my_temp_table
    SELECT first_name FROM people WHERE last_name = 'Smith';

(Див. Також Створення тимчасової таблиці з оператора select без використання Створення таблиці .)


1
Оххх: o Я не знав, що у SQL таке !! Таблиці живі лише для обсягу всіх запущених запитів. ЧИСТО!
iGbanam

2
@Yasky, це за умови, що ви не використовуватимете з'єднання повторно. Бо справді це триватиме протягом усього сеансу.
Pacerier


4
@ Джон: Так, ну, ти можеш використати його повторно, але не за тим самим запитом.
einpoklum

1
Якщо ви повторно використовуєте підключення, вам, як правило, слід ВПАДАТИ ТИМЧАСКУ ТАБЛИЦУ, ЯКЩО ІСНУЄ my_temp_table; перед його створенням.
Аураст

46

Ви можете досягти цього в MySQL за допомогою WHILEциклу:

SET @myArrayOfValue = '2,5,2,23,6,';

WHILE (LOCATE(',', @myArrayOfValue) > 0)
DO
    SET @value = ELT(1, @myArrayOfValue);
    SET @myArrayOfValue= SUBSTRING(@myArrayOfValue, LOCATE(',',@myArrayOfValue) + 1);

    INSERT INTO `EXEMPLE` VALUES(@value, 'hello');
END WHILE;

РЕДАГУВАТИ: Або ви можете це зробити, використовуючи UNION ALL:

INSERT INTO `EXEMPLE`
(
 `value`, `message`
)
(
 SELECT 2 AS `value`, 'hello' AS `message`
 UNION ALL
 SELECT 5 AS `value`, 'hello' AS `message`
 UNION ALL
 SELECT 2 AS `value`, 'hello' AS `message`
 UNION ALL
 ...
);

4
Хіба цикли неможливі лише в збережених процедурах?
einpoklum

2
так, це можливо всередині збережених процедур, функцій та тригерів.
Омеш,

1
Тож я не можу використовувати код, який ви надали ... Мені потрібне щось, що застосовується загальніше.
einpoklum

Ви можете написати зразок збереженої процедури та CALLїї.
Омеш,

1
Я не думаю, що масиви потрібні. Ви можете легко зробити це за допомогою тимчасових таблиць або UNION ALLбез використання процедури.
Омеш

28

Спробуйте використати функцію FIND_IN_SET () MySql, наприклад

SET @c = 'xxx,yyy,zzz';

SELECT * from countries 
WHERE FIND_IN_SET(countryname,@c);

Примітка: Вам не потрібно встановлювати змінну в StoredProcedure, якщо ви передаєте параметр зі значеннями CSV.


Остерігайтеся обмежень довжини, які можуть бути досить низькими: stackoverflow.com/q/2567000/1333493
Немо,

19

Сьогодні використання масиву JSON було б очевидною відповіддю.

Оскільки це давнє, але все ще актуальне питання, я навів короткий приклад. Функції JSON доступні з MySQL 5.7.x / MariaDB 10.2.3

Я віддаю перевагу цьому рішенню над ELT (), тому що воно насправді більше схоже на масив, і цей "масив" можна використовувати повторно в коді.

Але будьте обережні: це (JSON), безумовно, набагато повільніше, ніж використання тимчасової таблиці. Це просто більш зручно. imo.

Ось як використовувати масив JSON:

SET @myjson = '["gmail.com","mail.ru","arcor.de","gmx.de","t-online.de",
                "web.de","googlemail.com","freenet.de","yahoo.de","gmx.net",
                "me.com","bluewin.ch","hotmail.com","hotmail.de","live.de",
                "icloud.com","hotmail.co.uk","yahoo.co.jp","yandex.ru"]';

SELECT JSON_LENGTH(@myjson);
-- result: 19

SELECT JSON_VALUE(@myjson, '$[0]');
-- result: gmail.com

І ось невеликий приклад, щоб показати, як це працює у функції / процедурі:

DELIMITER //
CREATE OR REPLACE FUNCTION example() RETURNS varchar(1000) DETERMINISTIC
BEGIN
  DECLARE _result varchar(1000) DEFAULT '';
  DECLARE _counter INT DEFAULT 0;
  DECLARE _value varchar(50);

  SET @myjson = '["gmail.com","mail.ru","arcor.de","gmx.de","t-online.de",
                "web.de","googlemail.com","freenet.de","yahoo.de","gmx.net",
                "me.com","bluewin.ch","hotmail.com","hotmail.de","live.de",
                "icloud.com","hotmail.co.uk","yahoo.co.jp","yandex.ru"]';

  WHILE _counter < JSON_LENGTH(@myjson) DO
    -- do whatever, e.g. add-up strings...
    SET _result = CONCAT(_result, _counter, '-', JSON_VALUE(@myjson, CONCAT('$[',_counter,']')), '#');

    SET _counter = _counter + 1;
  END WHILE;

  RETURN _result;
END //
DELIMITER ;

SELECT example();

Ви хочете сказати, що ELT повільніший або JSON повільніший?
Канагавелу Сугумар

2
@Kanagavelu Sugumar: На момент написання JSON, безумовно, працює повільніше. Я відредагував відповідь, щоб зробити це зрозумілішим.
SeparateReality

16

Не знаю про масиви, але є спосіб зберігати розділені комами списки у звичайному стовпці VARCHAR.

І коли вам потрібно знайти щось у цьому списку, ви можете використовувати функцію FIND_IN_SET () .


Якщо я хочу знайти підмножину в наборі, чи є спосіб?
Akshay Vishnoi

Вибачте! Я не впевнений, що це можливо.
wormhit

У вас найкраще рішення
Кальвін,

7
DELIMITER $$
CREATE DEFINER=`mysqldb`@`%` PROCEDURE `abc`()
BEGIN
  BEGIN 
    set @value :='11,2,3,1,'; 
    WHILE (LOCATE(',', @value) > 0) DO
      SET @V_DESIGNATION = SUBSTRING(@value,1, LOCATE(',',@value)-1); 
      SET @value = SUBSTRING(@value, LOCATE(',',@value) + 1); 
      select @V_DESIGNATION;
    END WHILE;
  END;
END$$
DELIMITER ;

2
Поясніть, будь ласка, як використовувати цей код і як він відповідає на запитання.
einpoklum

Як і тут, ви робите просту процедуру, яка дає один за одним елемент конкретного рядка, який працює як масив в Oracle.
Сагар Гангвал

Oracle? Це питання не про Oracle. Крім того, схоже, ви визначаєте масив в рамках процедури.
einpoklum

Будь ласка, перевірте Syntex, це лише для mysql
Сагар Гангвал

Не пропустіть останню кому!
Eagle_Eye

4

Я знаю, що це трохи пізня реакція, але нещодавно мені довелося вирішити подібну проблему і думав, що це може бути корисно для інших.

Передумови

Розглянемо таблицю нижче, що називається "mytable":

Стартовий стіл

Проблема полягала в тому, щоб зберегти лише останні 3 записи та видалити будь-які попередні записи, системний = 1 (у таблиці може бути багато інших записів з іншими системними значеннями)

Було б добре, якщо б ви могли зробити це, просто використовуючи заяву

DELETE FROM mytable WHERE id IN (SELECT id FROM `mytable` WHERE systemid=1 ORDER BY id DESC LIMIT 3)

Однак це ще не підтримується в MySQL, і якщо ви спробуєте це, ви отримаєте повідомлення про помилку

...doesn't yet support 'LIMIT & IN/ALL/SOME subquery'

Отже, необхідний обхідний шлях, завдяки якому масив значень передається в селектор IN за допомогою змінної. Однак, оскільки змінні повинні бути одиничними значеннями, мені потрібно було б імітувати масив . Фокус полягає в тому, щоб створити масив у вигляді списку значень, відокремлених комами (рядок), і призначити це змінній наступним чином

SET @myvar := (SELECT GROUP_CONCAT(id SEPARATOR ',') AS myval FROM (SELECT * FROM `mytable` WHERE systemid=1 ORDER BY id DESC LIMIT 3 ) A GROUP BY A.systemid);

Результатом, що зберігається в @myvar, є

5,6,7

Далі селектор FIND_IN_SET використовується для вибору із змодельованого масиву

SELECT * FROM mytable WHERE FIND_IN_SET(id,@myvar);

Сукупний кінцевий результат такий:

SET @myvar := (SELECT GROUP_CONCAT(id SEPARATOR ',') AS myval FROM (SELECT * FROM `mytable` WHERE systemid=1 ORDER BY id DESC LIMIT 3 ) A GROUP BY A.systemid);
DELETE FROM mytable WHERE FIND_IN_SET(id,@myvar);

Мені відомо, що це дуже конкретний випадок. Однак його можна модифікувати так, щоб він відповідав практично будь-якому іншому випадку, коли змінна повинна зберігати масив значень.

Я сподіваюся, що це допоможе.


3

Можливо, створіть тимчасову таблицю пам'яті зі стовпцями (ключ, значення), якщо ви хочете асоціативні масиви. Наявність таблиці пам'яті - це найближче до масивів у mysql


М-м-м, я не хочу асоціативних масивів, просто масиви.
einpoklum

Ви можете використовувати тимчасову таблицю пам'яті лише з одним стовпцем, а потім прокрутити значення через курсори, тобто це найближче до використання масивів та циклів for / while у
недекларативній

Мова насправді має цю особливість, тобто немає жодної синтаксичної причини, через яку ви не могли б вибрати вектор у змінну так само, як ви вибрали скаляр для неї.
einpoklum

3

Ось як я це зробив.

Спочатку я створив функцію, яка перевіряє, чи є Long / Integer / будь-яке значення у списку значень, розділених комами:

CREATE DEFINER = 'root'@'localhost' FUNCTION `is_id_in_ids`(
        `strIDs` VARCHAR(255),
        `_id` BIGINT
    )
    RETURNS BIT(1)
    NOT DETERMINISTIC
    CONTAINS SQL
    SQL SECURITY DEFINER
    COMMENT ''
BEGIN

  DECLARE strLen    INT DEFAULT 0;
  DECLARE subStrLen INT DEFAULT 0;
  DECLARE subs      VARCHAR(255);

  IF strIDs IS NULL THEN
    SET strIDs = '';
  END IF;

  do_this:
    LOOP
      SET strLen = LENGTH(strIDs);
      SET subs = SUBSTRING_INDEX(strIDs, ',', 1);

      if ( CAST(subs AS UNSIGNED) = _id ) THEN
        -- founded
        return(1);
      END IF;

      SET subStrLen = LENGTH(SUBSTRING_INDEX(strIDs, ',', 1));
      SET strIDs = MID(strIDs, subStrLen+2, strLen);

      IF strIDs = NULL or trim(strIds) = '' THEN
        LEAVE do_this;
      END IF;

  END LOOP do_this;

   -- not founded
  return(0);

END;

Тож тепер ви можете шукати ідентифікатор у списку ідентифікаторів, розділених комами, наприклад:

select `is_id_in_ids`('1001,1002,1003',1002);

І ви можете використовувати цю функцію всередині речення WHERE, наприклад:

SELECT * FROM table1 WHERE `is_id_in_ids`('1001,1002,1003',table1_id);

Це був єдиний спосіб, який я знайшов, щоб передати параметр "масив" у ПРОЦЕДУРУ.


2

Хіба сенс масивів не бути ефективним? Якщо ви просто перебираєте значення, я думаю, що курсор на тимчасовій (або постійній) таблиці має більше сенсу, ніж пошук коми, ні? Також чистіше. Пошук "mysql ОБ'ЯВИТИ КУРСОР".

Для довільного доступу тимчасова таблиця з числовим індексом первинного ключа. На жаль, найшвидший доступ, який ви отримаєте, - це хеш-таблиця, а не справжній довільний доступ.


Це коментар, а не відповідь. Я не вказав, що саме це я хочу робити з масивом.
einpoklum

2

Я здивований, що жодна з відповідей не згадує ELT / FIELD.

ELT / FIELD працює дуже схоже на масив, особливо якщо у вас є статичні дані.

FIND_IN_SET також працює подібним чином, але не має вбудованої додаткової функції, але досить просто написати її.

mysql> select elt(2,'AA','BB','CC');
+-----------------------+
| elt(2,'AA','BB','CC') |
+-----------------------+
| BB                    |
+-----------------------+
1 row in set (0.00 sec)

mysql> select field('BB','AA','BB','CC');
+----------------------------+
| field('BB','AA','BB','CC') |
+----------------------------+
|                          2 |
+----------------------------+
1 row in set (0.00 sec)

mysql> select find_in_set('BB','AA,BB,CC');
+------------------------------+
| find_in_set('BB','AA,BB,CC') |
+------------------------------+
|                            2 |
+------------------------------+
1 row in set (0.00 sec)

mysql>  SELECT SUBSTRING_INDEX(SUBSTRING_INDEX('AA,BB,CC',',',2),',',-1);
+-----------------------------------------------------------+
| SUBSTRING_INDEX(SUBSTRING_INDEX('AA,BB,CC',',',2),',',-1) |
+-----------------------------------------------------------+
| BB                                                        |
+-----------------------------------------------------------+
1 row in set (0.01 sec)

1

Це добре працює для списку значень:

SET @myArrayOfValue = '2,5,2,23,6,';

WHILE (LOCATE(',', @myArrayOfValue) > 0)
DO
SET @value = ELT(1, @myArrayOfValue);
    SET @STR = SUBSTRING(@myArrayOfValue, 1, LOCATE(',',@myArrayOfValue)-1);
    SET @myArrayOfValue = SUBSTRING(@myArrayOfValue, LOCATE(',', @myArrayOfValue) + 1);

    INSERT INTO `Demo` VALUES(@STR, 'hello');
END WHILE;

1

Обидві версії з використанням наборів для мене не працювали (протестовано з MySQL 5.5). Функція ELT () повертає весь набір. Враховуючи, що оператор WHILE доступний лише в контексті PROCEDURE, я додав його до свого рішення:

DROP PROCEDURE IF EXISTS __main__;

DELIMITER $
CREATE PROCEDURE __main__()
BEGIN
    SET @myArrayOfValue = '2,5,2,23,6,';

    WHILE (LOCATE(',', @myArrayOfValue) > 0)
    DO
        SET @value = LEFT(@myArrayOfValue, LOCATE(',',@myArrayOfValue) - 1);    
        SET @myArrayOfValue = SUBSTRING(@myArrayOfValue, LOCATE(',',@myArrayOfValue) + 1);
    END WHILE;
END;
$
DELIMITER ;

CALL __main__;

Чесно кажучи, я не думаю, що це хороша практика. Навіть якщо це дійсно необхідно, це ледве читається і досить повільно.


1

Ще один спосіб побачити ту саму проблему. Надія корисна

DELIMITER $$
CREATE PROCEDURE ARR(v_value VARCHAR(100))
BEGIN

DECLARE v_tam VARCHAR(100);
DECLARE v_pos VARCHAR(100);

CREATE TEMPORARY TABLE IF NOT EXISTS split (split VARCHAR(50));

SET v_tam = (SELECT (LENGTH(v_value) - LENGTH(REPLACE(v_value,',',''))));
SET v_pos = 1;

WHILE (v_tam >= v_pos)
DO
    INSERT INTO split 
    SELECT SUBSTRING_INDEX(SUBSTRING_INDEX(v_value,',',v_pos),',', -1);
    SET v_pos = v_pos + 1;
END WHILE;

SELECT * FROM split;

DROP TEMPORARY TABLE split;

END$$


CALL ARR('1006212,1006404,1003404,1006505,444,');

Насправді, незрозуміло, що ви тут говорите. Це питання 7 років тому має кілька відповідних відповідей. Подумайте про те, щоб видалити свою відповідь або пояснити те, що ви намагаєтесь повідомити нам безпосередньо / загалом, а не на прикладі.
einpoklum

0

У версії MYSQL після 5.7.x ви можете використовувати тип JSON для зберігання масиву. Ви можете отримати значення масиву за допомогою ключа за допомогою MYSQL.


7
Можете навести приклад, як я це міг би зробити?
einpoklum

0

Натхненний функцією ELT (номер індексу, рядок1, рядок2, рядок3,…), я думаю, що наступний приклад працює як приклад масиву:

set @i := 1;
while @i <= 3
do
  insert into table(val) values (ELT(@i ,'val1','val2','val3'...));
set @i = @i + 1;
end while;

Сподіваюся, це допоможе.


0

Ось приклад для MySQL для циклу через рядок, розділений комами.

DECLARE v_delimited_string_access_index INT;
DECLARE v_delimited_string_access_value VARCHAR(255);
DECLARE v_can_still_find_values_in_delimited_string BOOLEAN;

SET v_can_still_find_values_in_delimited_string = true;
SET v_delimited_string_access_index = 0;
WHILE (v_can_still_find_values_in_delimited_string) DO
  SET v_delimited_string_access_value = get_from_delimiter_split_string(in_array, ',', v_delimited_string_access_index); -- get value from string
  SET v_delimited_string_access_index = v_delimited_string_access_index + 1;
  IF (v_delimited_string_access_value = '') THEN
    SET v_can_still_find_values_in_delimited_string = false; -- no value at this index, stop looping
  ELSE
    -- DO WHAT YOU WANT WITH v_delimited_string_access_value HERE
  END IF;
END WHILE;

тут використовується get_from_delimiter_split_stringфункція, визначена тут: https://stackoverflow.com/a/59666211/3068233


Рядки з розділеними комами вже пропонувались - роки тому.
einpoklum

@einpoklum yep - і ось ще один спосіб взаємодії з ними
Ulad Kasach

0

Чи справді необхідна змінна масиву?

Я запитую, тому що я спочатку приземлився тут, бажаючи додати масив як змінну таблиці MySQL. Я був відносно новим у розробці баз даних і намагався подумати, як би це зробити типовою мовою програмування.

Але бази даних бувають різні. Я думав, що хочу масив як змінну, але виявляється, це просто не звичайна практика баз даних MySQL.

Стандартна практика

Альтернативним рішенням для масивів є додавання додаткової таблиці, а потім посилання на вихідну таблицю зовнішнім ключем.

Як приклад, уявімо собі програму, яка відстежує всі предмети, які кожна людина в домогосподарстві хоче придбати в магазині.

Команди для створення таблиці, яку я спочатку передбачав, мали б виглядати приблизно так:

#doesn't work
CREATE TABLE Person(
  name VARCHAR(50) PRIMARY KEY
  buy_list ARRAY
);

Я думаю, що я задумав buy_list як рядок елементів, розділених комами, або щось подібне.

Але MySQL не має поля типу масиву, тому мені дійсно потрібно було щось подібне:

CREATE TABLE Person(
  name VARCHAR(50) PRIMARY KEY
);
CREATE TABLE BuyList(
  person VARCHAR(50),
  item VARCHAR(50),
  PRIMARY KEY (person, item),
  CONSTRAINT fk_person FOREIGN KEY (person) REFERENCES Person(name)
);

Тут ми визначаємо обмеження з іменем fk_person. Там сказано, що поле "особа" в BuyList - це зовнішній ключ. Іншими словами, це первинний ключ в іншій таблиці, зокрема поле "ім'я" в таблиці Person, що і позначає REFERENCES.

Ми також визначили поєднання особи та предмета як первинний ключ, але технічно це не потрібно.

Нарешті, якщо ви хочете отримати всі елементи у списку людини, ви можете запустити цей запит:

SELECT item FROM BuyList WHERE person='John';

Це дає вам усі пункти зі списку Джона. Не потрібно масивів!


Моє прийняте рішення - використовувати тимчасову таблицю.
einpoklum

Звичайно. Потім я включив цю відповідь для всіх, як я, хто потрапив на цю сторінку, шукаючи спосіб створити тип масиву - хто спочатку не розумів, чому масиви не є типом у MySQL. Це за задумом, здається. Загальний випадок тут не був представлений, тому я включив те, що дізнався, щоб інші зрозуміли, що масиви зазвичай не потрібні. Я не очікую, що ви оберете мою відповідь. Це залежить від випадку використання. У вас є прийнята відповідь для конкретного випадку використання, і я надаю цю відповідь для загального випадку використання.
kraftydevil

0

Якщо у нас є одна така таблиця

mysql> select * from user_mail;
+------------+-------+
| email      | user | 
+------------+-------+-
| email1@gmail |     1 | 
| email2@gmail |     2 |
+------------+-------+--------+------------+

та таблиця масивів:

mysql> select * from user_mail_array;
+------------+-------+-------------+
| email      | user | preferences |
+------------+-------+-------------+
| email1@gmail |     1 |           1 |
| email1@gmail |     1 |           2 |
| email1@gmail |     1 |           3 |
| email1@gmail |     1 |           4 |
| email2@gmail |     2 |           5 |
| email2@gmail |     2 |           6 |

Ми можемо вибрати рядки другої таблиці як один масив із функцією CONCAT:

mysql> SELECT t1.*, GROUP_CONCAT(t2.preferences) AS preferences
     FROM user_mail t1,user_mail_array t2
       where t1.email=t2.email and t1.user=t2.user
     GROUP BY t1.email,t1.user;

+------------+-------+--------+------------+-------------+
| email      | user | preferences |
+------------+-------+--------+------------+-------------+
|email1@gmail |     1 | 1,3,2,4     |
|email2@gmail |     2 | 5,6         |
+------------+-------+--------+------------+-------------+

Думаю, дублікат відповіді Клінтона.
einpoklum

-2

Я думаю, що зможу покращити цю відповідь. Спробуйте це:

Параметр "Витівки" - це CSV. тобто '1,2,3,4 ..... тощо'

CREATE PROCEDURE AddRanks(
IN Pranks TEXT
)
BEGIN
  DECLARE VCounter INTEGER;
  DECLARE VStringToAdd VARCHAR(50);
  SET VCounter = 0;
  START TRANSACTION;
  REPEAT
    SET VStringToAdd = (SELECT TRIM(SUBSTRING_INDEX(Pranks, ',', 1)));
    SET Pranks = (SELECT RIGHT(Pranks, TRIM(LENGTH(Pranks) - LENGTH(SUBSTRING_INDEX(Pranks, ',', 1))-1)));
    INSERT INTO tbl_rank_names(rank)
    VALUES(VStringToAdd);
    SET VCounter = VCounter + 1;
  UNTIL (Pranks = '')
  END REPEAT;
  SELECT VCounter AS 'Records added';
  COMMIT;
END;

Цей метод робить пошуковий рядок значень CSV поступово коротшим із кожною ітерацією циклу, що, на мою думку, було б краще для оптимізації.


До чого ви маєте на увазі цю відповідь? Крім того, ви не маєте мати файл CSV.
einpoklum

Я не посилався на файл CSV, я мав на увазі значення CSV, таке як "1,2,3,4 ... і т.д."
user2288580

-2

Я б спробував щось подібне для кількох колекцій. Я початківець MySQL. Вибачте за назви функцій, не зміг визначити, які імена будуть найкращими.

delimiter //

drop  procedure init_
//
create procedure init_()
begin
  CREATE TEMPORARY TABLE if not exists 
    val_store(  
    realm  varchar(30) 
    ,  id  varchar(30) 
    ,  val   varchar(255) 
    ,  primary key ( realm , id )
    );
end;
//

drop function if exists get_
//
create function get_( p_realm varchar(30) , p_id varchar(30) )
  returns varchar(255)
  reads sql data
begin 
  declare ret_val varchar(255);
  declare continue handler for 1146 set ret_val = null;
  select val into ret_val from val_store where id = p_id;
  return ret_val;
end;
//

drop procedure if exists set_
//
create procedure set_( p_realm varchar(30) , p_id varchar(30) , p_val varchar(255) )
begin
  call init_(); 
  insert into val_store (realm,id,val) values (p_realm , p_id , p_val) on duplicate key update val = p_val;
end;
//

drop   procedure if exists remove_
//
create procedure remove_( p_realm varchar(30) , p_id varchar(30) )
begin
  call init_();
  delete from val_store where realm = p_realm and id = p_id;
end;
//

drop   procedure if exists erase_
//
create procedure erase_( p_realm varchar(30) ) 
begin
  call init_();
  delete from val_store where realm = p_realm;
end;
//

call set_('my_array_table_name','my_key','my_value');

select get_('my_array_table_name','my_key');

Думаю, я розумію, що ви пропонуєте, але це досить громіздко і, мабуть, також неймовірно повільно ...
einpoklum

Я не можу схвалити або відхилити його без стрес-тестування. В основному це пошук і вставка первинного ключа у тимчасовій таблиці (або звичайній таблиці). Я буду користуватися ним, поки не зіткнуся з проблемами або не знайду кращого шляху; але я роблю дивні речі, такі як компілятори записів та ігри, повністю в Oracle PL / SQL.
Дейв

-2

Замість того, щоб зберігати дані як масив або лише в одному рядку, ви повинні робити різні рядки для кожного отриманого значення. Це значно спростить розуміння, а не поєднання всіх.


Поділіться, будь ласка, як це зробити
Ніко Хаасе,

-5

Ви пробували використовувати PHP's serialize ()? Це дозволяє зберігати вміст масиву змінної у рядку, який розуміє PHP, і є безпечним для бази даних (якщо припустити, що ви його вникли першими).

$array = array(
    1 => 'some data',
    2 => 'some more'
);

//Assuming you're already connected to the database
$sql = sprintf("INSERT INTO `yourTable` (`rowID`, `rowContent`) VALUES (NULL, '%s')"
     ,  serialize(mysql_real_escape_string($array, $dbConnection)));
mysql_query($sql, $dbConnection) or die(mysql_error());

Ви можете зробити те саме те саме без нумерованого масиву

$array2 = array(
    'something' => 'something else'
);

або

$array3 = array(
    'somethingNew'
);

7
Я не працюю з PHP, тому це для мене насправді не актуально.
einpoklum

1
Використовуйте JSON замість серіалізації. Він є більш загальним та незалежним від мови.
Рік Джеймс,
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.