Форум: Форум PHPФорум ApacheФорум Регулярные ВыраженияФорум MySQLHTML+CSS+JavaScriptФорум FlashРазное
Новые темы: 0000000
PHP на примерах (2 издание). Авторы: Кузнецов М.В., Симдянов И.В. PHP Puzzles. Авторы: Кузнецов М.В., Симдянов И.В. PHP 5/6. В подлиннике. Авторы: Кузнецов М.В., Симдянов И.В. PHP 5. На примерах. Авторы: Кузнецов М.В., Симдянов И.В., Голышев С.В. Самоучитель MySQL 5. Авторы: Кузнецов М.В., Симдянов И.В.
ВСЕ НАШИ КНИГИ
Консультационный центр SoftTime

Форум MySQL

Выбрать другой форум

 

Здравствуйте, Посетитель!

вид форума:
Линейный форум Структурный форум

тема: Разложить данные в таблицу
 
 автор: Лена   (27.12.2010 в 12:01)   письмо автору
 
 

Прошу помощи, перепробовала все, что только можно.
Есть данные в таблице MySQL. Структура таблицы такая:

CREATE TABLE `rnt1_room_attrs` (
  `id` int(11) NOT NULL auto_increment,
  `price` int(11) default NULL,
  `date_start` date default NULL,
  `date_end` date NOT NULL,
  `id_room` int(11) default NULL,
  `id_hotel` int(11) NOT NULL,
  `visible` varchar(2) default NULL,
  PRIMARY KEY  (`id`),
  KEY `id_hotel` (`id_hotel`),
  KEY `id_room` (`id_room`),
  KEY `id_room_2` (`id_room`)
) ENGINE=MyISAM AUTO_INCREMENT=9 DEFAULT CHARSET=utf8 AUTO_INCREMENT=9 ; 


Надо эти данные запихнуть в таблицу таким образом:
 
-- ----------------------------------------------------------------
 Название отеля     | Диапазон1| Диапазон2 | Диапазон3 | Диапазон4
-------------------------------------------------------------------
  Комната 1            |цена1     |цена2      | цена3     | цена4 |  
  Комната 2            |цена1     |цена2      | цена3     | цена4 |


На пересечении комнаты и даты - цена за эту комнату в определенный диапазон, т.е. это - одна строка в таблице MySQL,
т.е., учитывая поля таблицы MySQL, все должно выглядеть так:

-- -------------------------------------------------------------------------------------
 id_hotel               | date_start-date_end | date_start-date_end | date_start-date_end
                        |                     |                     | 
-----------------------------------------------------------------------------------------
  id_room               |price                |price                | price      
  id_room               |price                |price                | price    



Название отеля по его id_hotel - в другой таблице, как и тип комнаты, я эти таблицы позже через JOIN подключу, сейчас надо вытянуть и разложить хотя бы из одной таблицы. Основная трудность в том, что таблицу надо разложить одновременно и по горизонтали, и по вертикали.

  Ответить  
 
 автор: Trianon   (27.12.2010 в 13:08)   письмо автору
 
   для: Лена   (27.12.2010 в 12:01)
 

Предполагается, что в таблице MySQL больше одного отеля.

В то же время, таблица результата (HTML наверное) выглядит так, как будто отель всего один.

Или задачу следует решить "для определенного $id_hotel" ?

  Ответить  
 
 автор: Лена   (27.12.2010 в 13:33)   письмо автору
 
   для: Trianon   (27.12.2010 в 13:08)
 

Да, отелей много, как и типов комнат в них. Я привела пример с одним отелем. И запихивать в таблицу надо все отели.


-- ------------------------------------------------------------------------------------- 
 id_hotel 1              | date_start-date_end | date_start-date_end | date_start-date_end 
                        |                     |                     |  
----------------------------------------------------------------------------------------- 
  id_room               |price                |price                | price       
  id_room               |price                |price                | price    

-- ------------------------------------------------------------------------------------- 
 id_hotel  2             | date_start-date_end | date_start-date_end | date_start-date_end 
                        |                     |                     |  
----------------------------------------------------------------------------------------- 
  id_room               |price                |price                | price       
  id_room               |price                |price                | price    

  Ответить  
 
 автор: Trianon   (27.12.2010 в 13:43)   письмо автору
 
   для: Лена   (27.12.2010 в 13:33)
 

>Да, отелей много, как и типов комнат в них. Я привела пример с одним отелем.

Вот пример кода для одного отеля.
<?php


  $table_prices 
'rntl_room_attrs';
  
$table_hotels '???';
  
$table_rooms '???';
 
  
  
$sql "
  SELECT hotel_name 
    FROM `
$table_hotels
    WHERE id = "
. ((int)$id_hotel);
  
$res mysql_query($sql); or die ... ;
  
$hotel_name htmlspecialchars(mysql_result(mysql_query($sql)));
  
$s "<table><tr><td> $hotel_name </td>";

  
  
$sql "
  SELECT DISTINCT CONCAT(`date_start`, '|', `date_end`) AS `range`, 
            FROM `
$table_prices`  
            WHERE `id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `range`
          "

  
$res mysql_query($sql); or die $sql.':'.mysql_error();
  for(
ranges=array(); ($row mysql_fetch_assoc($res)); )
     
$ranges[] = row['range']);

  foreach(
$ranges as $r)
       
$s .= "<td>".
    
//  format_range
      
($r)."</td>";
  
$s .= "</tr>\r\n";  
  
  
  
$sql "
  SELECT 
          `tr`.`name`,  
          CONCAT(`date_start`, '|', `date_end`) AS `range`, 
          `price`
            FROM `
$table_prices` `pl` 
              LEFT JOIN  `
$table_rooms` `tr` ON `pl`.`id_room` = `tr`.`id`
            WHERE `pl`.`id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `tr`.`room_seq`, `range` 
          "

  
$res mysql_query($sql); or die $sql.':'.mysql_error();
  
$pricelist = array();
  while(
$row mysql_fetch_assoc($res))
  {
      
$room $row['name'];
      
$range $row['range'];
      
$pricelist[$room][$range] = $row['price'];
  }
  
  foreach(
$pricelist as $room -> $list)
  {
    
$s .= "<tr><td>"htmlspecialchars($room)."</td>";
    foreach(
$ranges as $arnge)
    {
        
$price = isset($list[$range])
                   ? 
$list[$range] : "--";
        
$s .= "<td>".  htmlspecialchars($price) . "</td>";
    }
    
$s .= "</tr>\r\n";
  }    
  
$s .= "</table>\r\n";

 echo 
$s;

              

?>



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

PS. Естественно, не проверялось.
Потому что данных приведено едва ли не одна шестая часть.

  Ответить  
 
 автор: Лена   (27.12.2010 в 15:40)   письмо автору
 
   для: Trianon   (27.12.2010 в 13:43)
 

>PS. Естественно, не проверялось.
Потому что данных приведено едва ли не одна шестая часть.

Прошу прощения, не думала, что другие таблицы тоже сразу нужны. Скрипт подправила.

Получилось.
Мне попутно надо к каждому элементу, который отображается на странице, вытянуть его id из соответствующей таблицы. Сделала такой массив: $pricelist[$room."_".$idr][$range] = $row['price'] . "_" . $idp;

<?php
  $table_prices 
'rnt1_room_attrs';
  
$table_hotels 'rnt1_hotel';
  
$table_rooms 'rnt1_room';
  
$id_hotel 1;

  
$sql "
  SELECT name,id
    FROM `
$table_hotels`
    WHERE id = "
. ((int)$id_hotel);
  
$res mysql_query($sql) or die(mysql_error());

  
$hotel_name mysql_fetch_assoc($res);
  
$s "<table border='1'><tr><td><a href='?id=" $hotel_name['id'] . "'>" htmlspecialchars($hotel_name['name']) . "</a></td>";

  
$sql "
  SELECT DISTINCT CONCAT(`date_start`, '|', `date_end`) AS `range`,id
            FROM `
$table_prices`
            WHERE `id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `range`
          "
;
  
$res mysql_query($sql) or die($sql.':'.mysql_error());
  for(
$ranges=array(); ($row mysql_fetch_assoc($res)); )
     
$ranges$row['id']] = $row['range'];

  foreach(
$ranges as $k=>$r)
       
$s .= "<td><a href='?id_d=" $k "'>".

    
//format_range
      
($r)."</td>";
  
$s .= "</tr>\r\n";


  
$sql "
  SELECT
          `tr`.`type_room`,`tr`.`id` tid,`pl`.`id` pid,
          CONCAT(`date_start`, '|', `date_end`) AS `range`,
          `price`
            FROM `
$table_prices` `pl`
              LEFT JOIN  `
$table_rooms` `tr` ON `pl`.`id_room` = `tr`.`id`
            WHERE `pl`.`id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `tr`.`id`, `range`
          "
;
  
$res mysql_query($sql) or die( $sql.':'.mysql_error());
  
$pricelist = array();
  while(
$row mysql_fetch_assoc($res))
  {
      
$room $row['type_room'];
      
$range $row['range'];
      
$idr $row['tid'];    //ид комнаты
      
$idp $row['pid']; //ид цены

      
$pricelist[$room."_".$idr][$range] = $row['price'] . "_" $idp;
  }

  foreach(
$pricelist as $room => $list){

        
$expl1 explode("_",$room);

    
$s .= "<tr><td><a href='?tid=" $expl1[1] . "'>"htmlspecialchars($expl1[0])."</a></td>";
    foreach(
$ranges as $range)
    {
       if(isset(
$list[$range])){
       
$rrr explode("_"$list[$range]);
       
$price =  $list[$range];
       }else{
       
$price "--";
       }


        
$s .= "<td><a href='?pid=" $rrr[1] . "'>".  htmlspecialchars($rrr[0]) . "</a></td>";
    }
    
$s .= "</tr>\r\n";
  }
  
$s .= "</table>\r\n";

 echo 
$s;
?>

  Ответить  
 
 автор: Trianon   (27.12.2010 в 15:57)   письмо автору
 
   для: Лена   (27.12.2010 в 15:40)
 

>Мне попутно надо к каждому элементу, который отображается на странице, вытянуть его id из соответствующей таблицы. Сделала такой массив: $pricelist[$room."_".$idr][$range] = $row['price'] . "_" . $idp;

Если первичный ключ вытянут так или иначе - по нему и нужно строить связь.
while($row = mysql_fetch...
{
 $pricelist[$idr][$range] = $idp; 
 $rooms[$idr] = $room;
 $prices[$idp] = $row['price'];
}

  Ответить  
 
 автор: Лена   (27.12.2010 в 16:25)   письмо автору
 
   для: Trianon   (27.12.2010 в 15:57)
 


<?
  
foreach($pricelist as $room => $list)
  {
      if(
$rooms[$room]){
    
$s .= "<tr><td><a href='?tid=" $room "'>"htmlspecialchars($rooms[$room])."</a></td>";
      }

    foreach(
$ranges as $range){
      if(isset(
$list[$range]))
        
$pric_hotel = isset($prices[$list[$range]])
                   ? 
$prices[$list[$range]] : "--";

        
$s .= "<td><a href='?pid=" $list[$range] . "'>".  htmlspecialchars($pric_hotel) . "</a></td>";

    }

Цена почему-то неправильно выводится. И даты.
Мне кажется, дело в этом запросе:
SELECT DISTINCT CONCAT(`date_start`, '|', `date_end`) AS `range`,id
если просто DISTINCT CONCAT(`date_start`, '|', `date_end`) AS `range` - все было правильно. Просто сейчас все даты, даже одинаковые, выводятся в отдельную колонку.
Чуть позже пристальней посмотрю, отпишусь.

  Ответить  
 
 автор: Trianon   (27.12.2010 в 18:51)   письмо автору
 
   для: Лена   (27.12.2010 в 16:25)
 

id там лишний. И запятая - тожже.
Запятая моя. id - Ваш.

  Ответить  
 
 автор: Лена   (27.12.2010 в 23:06)   письмо автору
 
   для: Trianon   (27.12.2010 в 18:51)
 

Мне id мой нужен :)
Реально получить и дату ,и ид этой даты?

Цены выводятся не под нужной датой. Почему - не могу разобраться.

    foreach($ranges as $range){
      if(isset($list[$range])){

        $price_hotel = isset($prices[$list[$range]])? $prices[$list[$range]] : "--";

        $s .= "<td><a href='?pid=" . $list[$range] . "'>".htmlspecialchars($price_hotel) . "</a></td>";
       }
    }

  Ответить  
 
 автор: Trianon   (28.12.2010 в 01:47)   письмо автору
 
   для: Лена   (27.12.2010 в 23:06)
 

>Мне id мой нужен :)
>Реально получить и дату ,и ид этой даты?

В рассматриваемой таблице нет ключа даты.
Нет даже ключа диапазона.
Есть только ключ связки.



>Цены выводятся не под нужной датой. Почему - не могу разобраться.
Не под нужным диапазоном. Раз.

>
> foreach($ranges as $range){
> if(isset($list[$range])){
>
> $price_hotel = isset($prices[$list[$range]])? $prices[$list[$range]] : "--";
>
> $s .= "<td><a href='?pid=" . $list[$range] . "'>".htmlspecialchars($price_hotel) . "</a></td>";
> }
> }
>

этот код с учетом поправки 27.12.2010 в 15:57 или без?

  Ответить  
 
 автор: Лена   (28.12.2010 в 14:40)   письмо автору
5.5 Кб
 
   для: Trianon   (28.12.2010 в 01:47)
 

>В рассматриваемой таблице нет ключа даты.
>Нет даже ключа диапазона.
>Есть только ключ связки.

У каждого диапазона есть свой ид - т.е. для каждого диапазона - своя строка в таблице, которая имеет уникальный идентификатор.

>
>>Цены выводятся не под нужной датой. Почему - не могу разобраться.
>Не под нужным диапазоном. Раз.

Да, не под нужным диапазоном. Аттач с дампом привесила, там скрипт с изменениями на текущий момент, в конце скрипта - дамп и структура таблиц базы.

>этот код с учетом поправки 27.12.2010 в 15:57 или без?

да, с учетом поправки, чтобы к каждому элементу шел id.

  Ответить  
 
 автор: Trianon   (28.12.2010 в 19:57)   письмо автору
20.5 Кб
 
   для: Лена   (28.12.2010 в 14:40)
 

результат справа вверху ====>
<?php
  $table_prices 
'rnt1_room_attrs';
  
$table_hotels 'rnt1_hotel';
  
$table_rooms 'rnt1_room';
  
$id_hotel 1;
           require_once(
'tmp/dbconfig.php');
  
$sql "
  SELECT name,id
    FROM `
$table_hotels`
    WHERE id = "
. ((int)$id_hotel);
  
$res mysql_query($sql) or die(mysql_error());

  
$hotel_name mysql_fetch_assoc($res);
  
$s "<table border='1'><tr><td><a href='?id=" $hotel_name['id'] . "'>" htmlspecialchars($hotel_name['name']) . "</a></td>";

  
$sql "
  SELECT DISTINCT CONCAT(`date_start`, ' ... ', `date_end`) AS `range`
            FROM `
$table_prices`
            WHERE `id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `range`
          "
;
  
$res mysql_query($sql) or die($sql.':'.mysql_error());
  for(
$ranges=array(); ($row mysql_fetch_assoc($res)); )
     
$ranges[] = $row['range'];
    
// no  range table, 
    // no range keays  - use range content
  
foreach($ranges as $r)       
       
$s .= "\r\n  <td><a href='?id_d=" htmlspecialchars(rawurlencode($r)) . "'>"
         
.
    
//format_range
      
htmlspecialchars
      
($r)."</a></td>";
  
$s .= "</tr>\r\n";


  
$sql "
  SELECT
          `tr`.`type_room`,`tr`.`id` tid,`pl`.`id` pid,
          CONCAT(`date_start`, ' ... ', `date_end`) AS `range`,
          `pl`.`price`
            FROM `
$table_prices` `pl`
              LEFT JOIN  `
$table_rooms` `tr` ON `pl`.`id_room` = `tr`.`id`
            WHERE `pl`.`id_hotel` = "
.((int)$id_hotel)."
              ORDER BY `tr`.`id`, `range`
          "
;
  
$res mysql_query($sql) or die( $sql.':'.mysql_error());
  
$pricelist = array();    $rooms = array();
  while(
$row mysql_fetch_assoc($res))
  {
      
$room $row['type_room'];
      
$range $row['range'];
      
$price $row['price'];
      
$idr $row['tid'];    //room id
      
$idp $row['pid']; //link id
      
$pricelist[$idr][$range] = array('id'=>$idp'price' =>$price);
      
$rooms[$idr] = $room;
  }

  foreach(
$pricelist as $idr => $list)
  {
    
$s .= " <tr><td><a href='?rid=$idr'>"htmlspecialchars($rooms[$idr])."</a></td>";
    foreach(
$ranges as $range)
    {

       
$td = !isset($list[$range]) ?" -- "
                   
: (
                   
"<a href='?pid=".$list[$range]['id']." '>"
                   
.htmlspecialchars($list[$range]['price'])
                   .
"</a>"
                   
);
        
$s .= "\r\n  <td>$td</td>";
    }
    
$s .= "</tr>\r\n";
  }
  
$s .= "</table>\r\n";

 echo 
$s;
?>

  Ответить  
Rambler's Top100
вверх

Rambler's Top100 Яндекс.Метрика Яндекс цитирования