Рекурсивная ф-ция: подсчет общего кол-ва numrows

SiMM

Новичок
$sum += recc2(...)
Делай как сказано - разбор полётов, если понадобится, будет потом.
 

dadesign

Guest
PHP:
function recc2($id){ 
connect(); 
   $q = "select * from category where parent_id=$id order by id,name"; //извлекаем имя, id и родительский id
   $res = mysql_query($q) or die("query failed: ".mysql_error()); //запрашивем
   $nrows = mysql_num_rows($res); // подсчитываем количество ячеек


   if($nrows > 0){ // если результат не нулевой

   for ($x=0;$x<$nrows;$x++) // цикл по результам
   {	

	$row = mysql_fetch_array($res);
	$nrows+=recc2($row['id']);

	return $nrows;
   }

  	}
	else return $nrows=0;

}

echo recc2($id);
работает но не считает :)
 

SiMM

Новичок
Как всё запущено. Перечитай мои посты ещё раз внимательно, и сделай наконец так, как сказано, а не пиши отсебятину. Потому что то, что ты написал - будет возвращать черт знает что, как ты сам этого и просил (просил - читай как "написал программу"). И потом, не надо путать две разные вещи - количество полученных в результате запроса строк и суммарное количество потомков - это две абсолютно разные вещи.
 

dadesign

Guest
подсчитать число поддиректорий нижнего уровня... написано здорово :/


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

SiMM

Новичок
Господи, да каким же нужно быть "броневым"...
PHP:
function recc2($id){ 
   $q = "select * from category where parent_id=$id order by id,name";
   $res = mysql_query($q) or die("query failed: ".mysql_error());
   if (mysql_num_rows($res))
     for ($sum = 0; $row = mysql_fetch_assoc($res); )
       $sum += recc2($row['id']); 
   else return 1;
   return $sum; 
}
PS: connect() то там зачем?
 

dadesign

Guest
Гм... почему "броневым"... я кажется специально запостил темы в форум для новичков... ? :)

я например не знал, что возвращать $num нужно после всего... вне for и про mysql_fetch_assoc вообще ничего не знаю...

Спасибо доктор... но больной на грани срыва :)


P.S. connect - просто по быстрому ф-ция коннекта к базе, весь материал дома.. тепеь будет что пересмотреть...

P.P.S а return оказывается полезная вещь...
 

untied

Сдвинутый новичок
А что вы так прицепились к рекурсии? Я бы выбрал одним запросом все идентификаторы и родительские_идентификаторы в двумерный массив. А потом многократно сканировал его в поисках потомков заданного id, сохраняя очередного потомка в отдельный массив или хэш. Сканирование двумерного массива заканчивается, когда ни один новый потомок в результате очередного сканирования не будет добавлен. Потом просто смотрим размер хэша.
(разумеется, при каждом сканировании ищем не только потомков заданного id, но и потомков всех id, уже добавленных в хэш)
 

SiMM

Новичок
Автор оригинала: dadesign
Гм... почему "броневым"... я кажется специально запостил темы в форум для новичков... ? :)
Потому что я наивно полагал, что единственная твоя проблема - в рекурсии. Я ошибался.
я например не знал, что возвращать $num нужно после всего... вне for
Иначе какой-бы смысл был в цикле?
и про mysql_fetch_assoc вообще ничего не знаю...
Это не обязательно (к алгоритму это никакого отношения не имеет, просто привычка), а если интересно - можно подсмотреть в мануале по [m]mysql_fetch_assoc[/m]
connect - просто по быстрому ф-ция коннекта к базе
В функции то рекурсивной зачем его постоянно делать?
а return оказывается полезная вещь...
Интересно, а как ты без него собирался обойтись? Похоже, у тебя ещё и проблемы с областью видимости

-~{}~ 11.01.05 16:05:

Автор оригинала: untied
А что вы так прицепились к рекурсии?
По моему я уже говорил, что для более оптимального решения надо предоставлять побольше информации о задаче.
Я бы выбрал одним запросом все идентификаторы и родительские_идентификаторы в двумерный массив.
Это не всегда возможно.
А потом многократно сканировал его в поисках потомков заданного id
По твоему, для этого рекурсия бы не пригодилась? Ну ладно, написал бы ты это итеративно - но, имхо, рекурсия всё же наглядна. У человека же была проблема с рекурсией как таковой - а откуда берутся данные - вопрос десятый.
 

untied

Сдвинутый новичок
Ну я лишь вариант решения задачи предложил. К тому же рекурсия со вложенными запросами SQL будут работать дольше, чем один запрос и многократное сканирование массива.
 

SiMM

Новичок
untied, зависит от объёмов, думаю. Да и если говорить о больших объёмах и оптимизации - я уже предлагал nested sets ;)
 

dadesign

Guest
SiMM

функция возвращает 1 если нет потомков и 1 если есть один потомок... :)
 

SiMM

Новичок
Автор оригинала: dadesign
функция возвращает 1 если нет потомков и 1 если есть один потомок... :)
Это ты немножко врёшь, впрочем, ошибка всё равно имела место быть и вполне устранялась отладкой (PHP FAQ: Ничего не работает! Что делать???)
PHP:
function query($id){
  static $arr = array( 2 => array(0 => 'Продукты питания'),
                       4 => array(2 => 'Колбасы'),
                       6 => array(4 => 'Москва'),
                       5 => array(4 => 'Микоян'),
                      11 => array(0 => 'Книги'),
                      12 => array(11 => 'Фантастика'),
                      16 => array(12 => 'Лукьяненко'),
                      13 => array(11 => 'Фентези'),
                      14 => array(11 => 'Детективы'),
                       1 => array(0 => 'Электроника'),
                       7 => array(1 => 'Видаки'),
                       9 => array(7 => 'VHS'),
                      10 => array(7 => 'VHS-C'),
                      15 => array(10 => 'Аксессуары'),
                       8 => array(1 => 'ДВД'),
                     );
  $res = array();
  foreach ($arr as $k => $v)
    if (isset($v[$id]))
      $res[$k] = array('id' => $k);
  return $res;
}

function recc2($id){
   $res = query($id);
   if ($sum = count($res))
     for (; $row = array_shift($res); )
       $sum += recc2($row['id']);
   else return 0;
   return $sum;
}
echo recc2(0);
На mysql переделаешь сам, структура массива выбрана исключительно из соображения удобства, а не того, как надо.
 

dadesign

Guest
PHP:
function recc2($id){
   $q = "select * from category where parent_id=$id order by id,name"; 
   $res = mysql_query($q) or die("Query failed: ".mysql_error()); 
   
   if ($sum=mysql_num_rows($res)) 
     for (; $row = mysql_fetch_array($res); ) 
       $sum += recc2($row['id']); 
   else return 0; 
   return $sum; 
}

echo recc2($id);

так вроде работает :)
 
Сверху