Фильтровать массив php только по тем элементам, которые имеют значение, совпадающее с $ name в $ data - PullRequest
0 голосов
/ 28 июня 2018

У меня есть скрипт php, который собирает все папки в папке постов и превращает их в список.

У меня есть переменная $ postinfo_str, назначенная json-файлу для каждой папки, которую я использую для хранения даты публикации, информации о категории / теге и т. Д.

У меня также есть переменная $ pagetitle, назначенная файлу заголовка title.php для каждой папки. Скажем, я нахожусь на странице архива «Июнь 2018», текст в этом файле будет «Июнь 2018». Если я нахожусь на странице категории «Учебники», это будет текст в title.php.

В файле JSON у меня есть:

{
     "Arraysortdate": "YYYYMMDD",
     "Month": "Month YYYY",
     "Category": ["cat1", "cat2", "etc"]
 }

Я упорядочиваю массив от самого нового до самого старого, используя krsort с Arraysortdate в качестве ключа.

Как мне отфильтровать массив, используя $ pagetitle в качестве входных данных, чтобы определить, есть ли совпадение в $ postinfo_str, а если нет, удалить эту папку из массива?

Все, что я могу найти в отношении сортировки массива, это то, где информация в $ pageinfo_str - это в основном массив, и поэтому $ title является вводом, а вывод - совпадающим текстом из $ postinfo_str, тогда как я хочу выходные данные должны быть папками, в которых только текст $ postinfo_str соответствует тексту ввода ($ pagetitle).

Вот мой код. Имейте в виду, что это плоский файл, я не хочу, чтобы база данных достигала этого. См комментарии, если вы хотите объяснения.

<?php 

	$BASE_PATH = '/path/to/public_html';
	
	// initial array containing the dirs
	    $dirs = glob($BASE_PATH.'/testblog/*/posts/*', GLOB_ONLYDIR);

	// new array with date as key
	    $dirinfo_arr = [];
	    foreach ($dirs as $cdir) {

		// get current page title from file
		    $pagetitle = file_get_contents("includes/title.php");
	
		// get date & post info from file
		    $dirinfo_str = file_get_contents("$cdir/includes/post-info.json");
		    $dirinfo = json_decode($dirinfo_str, TRUE);

		// add current directory to the info array
		    $dirinfo['dir'] = $cdir;
		// add current dir to new array where date is the key
		    $dirinfo_arr[$dirinfo['Arraysortdate']] = $dirinfo;
	}
	// now we sort the new array
	    krsort($dirinfo_arr);

	    foreach($dirinfo_arr as $key=>$dir) {
	    	$dirpath = $dir['dir'];
		$dirpath = str_replace('/path/to/public_html/', '', $dirpath);

?>


       <!--HTML HERE SUCH AS--!>
       
           <a href="<?=$dirpath;?>"> TEXT </a><br>

<?php
};
?>

1 Ответ

0 голосов
/ 28 июня 2018

У меня проблемы с описанием вашей проблемы. Ваш пример кода немного сбивает с толку. Похоже, для каждой директории загружается одинаковое global includes/title.php. Это означает, что значение $pagetitle должно быть одинаковым на каждой итерации. Если это предназначено, вы, вероятно, должны переместить эту линию прямо за пределы цикла. Если файл содержит реальный код php, вам, вероятно, следует использовать

$pagetitle = include 'includes/title.php'; 

или что-то подобное. Если это не так, вы, вероятно, должны назвать его title.txt. Если это не один глобальный файл, вам, вероятно, следует добавить путь к file_get_contents / include. (Однако почему бы вам просто не добавить заголовок в структуру json?)

Я предполагаю, что это произошло случайно при попытке предоставить минимальный пример кода (?) ... В любом случае, мой ответ не будет идеальным, но, надеюсь, его можно будет адаптировать, когда его поймут. ; о)

Если вам нужны только элементы в вашем массиве, которые удовлетворяют определенным свойствам, у вас есть два варианта:

  1. не вставляйте эти элементы (в основном, ваш код)

    foreach ($dirs as $cdir) {
    
        // get current page title from file
        $pagetitle = file_get_contents("includes/title.php");
    
        // get date & post info from file
        $dirinfo_str = file_get_contents("$cdir/includes/post-info.json");
        $dirinfo = json_decode($dirinfo_str, TRUE);
    
        // add current directory to the info array
        $dirinfo['dir'] = $cdir;
        // add current dir to new array where date is the key
    
     // ------------ NEW --------------
        $filtercat = 'cat1';
        if(!in_array($filtercat, $dirinfo['Category'])) {
             continue;
        }
     // -------------------------------
    
        $dirinfo_arr[$dirinfo['Arraysortdate']] = $dirinfo;
    
  2. array_filter массив впоследствии, предоставляя анонимную функцию

     // ----- before cycling through $dirinfo_arr for output
     $filtercat = 'cat1';
     $filterfunc = function($dirinfo) use ($filtercat) {
         return in_array($filtercat, $dirinfo['Category']));
     }
    
     $dirinfo_arr = array_filter($dirinfo_arr, $filterfunc);
    

    Вы должны прочитать об анонимных функциях и о том, как вы предоставляете им локальные переменные, чтобы облегчить боль. Возможно, ваш вариант использования лучше подходит для array_reduce, что аналогично, за исключением того, что вы можете определить выход вашего «фильтра».

$new = array_filter($array, $func), это просто причудливый способ написания:

$new = [];
foreach($array as $key => $value) {
    if($func($value)) {
        $new[$key] = $value;
    }
}

обновление 1

в моих примерах кода вы можете заменить in_array($filtercat, $dirinfo['Category']) на in_array($pagetitle, $dirinfo) - если вы хотите сопоставить что-либо, что находится в json-struct (базовый уровень) - или на ($pagetitle == $dirinfo['Month']), если вы просто хотите сопоставить месяц .

обновление 2

Я понимаю, что вы, вероятно, только начинаете с php или даже программируете, поэтому концепция какой-то "огромной базы данных" может быть пугающей. Но, с другой стороны, файловая система - это, с определенной точки зрения, база данных. Тем не менее, он обычно довольно медленный по сравнению с ним и не предоставляет многих функций.

В долгосрочной перспективе я настоятельно рекомендую использовать базу данных. Если вам не нравится идея поместить ваши данные в «некоторый сервер базы данных», используйте sqlite. Тем не менее, существует кривая обучения, если вам никогда не приходилось иметь дело с базами данных раньше. В долгосрочной перспективе это будет стоить времени, потому что это упрощает многие вещи.

...