WordPress.org

Make WordPress Core

Changeset 38859


Ignore:
Timestamp:
10/21/16 11:11:42 (8 months ago)
Author:
swissspidy
Message:

General: Introduce a wp_list_sort() helper function.

In addition to wp_list_filter() for filtering a list of objects, and wp_list_pluck() for plucking a certain field out of each object in a list, this new function can be used for sorting a list of objects by specific fields. These functions are now all contained within the new WP_List_Util() class and wp_list_sort() is used in various parts of core for sorting lists.

Props flixos90, DrewAPicture, jorbin.
Fixes #37128.

Location:
trunk
Files:
2 added
9 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wp-includes/category-template.php

    r38828 r38859  
    9898     */ 
    9999    return apply_filters( 'get_the_categories', $categories, $id ); 
    100 } 
    101  
    102 /** 
    103  * Sort categories by name. 
    104  * 
    105  * Used by usort() as a callback, should not be used directly. Can actually be 
    106  * used to sort any term object. 
    107  * 
    108  * @since 2.3.0 
    109  * @access private 
    110  * 
    111  * @param object $a 
    112  * @param object $b 
    113  * @return int 
    114  */ 
    115 function _usort_terms_by_name( $a, $b ) { 
    116     return strcmp( $a->name, $b->name ); 
    117 } 
    118  
    119 /** 
    120  * Sort categories by ID. 
    121  * 
    122  * Used by usort() as a callback, should not be used directly. Can actually be 
    123  * used to sort any term object. 
    124  * 
    125  * @since 2.3.0 
    126  * @access private 
    127  * 
    128  * @param object $a 
    129  * @param object $b 
    130  * @return int 
    131  */ 
    132 function _usort_terms_by_ID( $a, $b ) { 
    133     if ( $a->term_id > $b->term_id ) 
    134         return 1; 
    135     elseif ( $a->term_id < $b->term_id ) 
    136         return -1; 
    137     else 
    138         return 0; 
    139100} 
    140101 
  • trunk/src/wp-includes/class-wp-customize-manager.php

    r38829 r38859  
    25062506     * 
    25072507     * @since 3.4.0 
     2508     * @deprecated 4.7.0 Use wp_list_sort() 
    25082509     * 
    25092510     * @param WP_Customize_Panel|WP_Customize_Section|WP_Customize_Control $a Object A. 
     
    25122513     */ 
    25132514    protected function _cmp_priority( $a, $b ) { 
     2515        _deprecated_function( __METHOD__, '4.7.0', 'wp_list_sort' ); 
     2516 
    25142517        if ( $a->priority === $b->priority ) { 
    25152518            return $a->instance_number - $b->instance_number; 
     
    25312534 
    25322535        $controls = array(); 
    2533         uasort( $this->controls, array( $this, '_cmp_priority' ) ); 
     2536        $this->controls = wp_list_sort( $this->controls, array( 
     2537            'priority'        => 'ASC', 
     2538            'instance_number' => 'ASC', 
     2539        ) ); 
    25342540 
    25352541        foreach ( $this->controls as $id => $control ) { 
     
    25442550 
    25452551        // Prepare sections. 
    2546         uasort( $this->sections, array( $this, '_cmp_priority' ) ); 
     2552        $this->sections = wp_list_sort( $this->sections, array( 
     2553            'priority'        => 'ASC', 
     2554            'instance_number' => 'ASC', 
     2555        ) ); 
    25472556        $sections = array(); 
    25482557 
     
    25522561            } 
    25532562 
    2554             usort( $section->controls, array( $this, '_cmp_priority' ) ); 
     2563 
     2564            $section->controls = wp_list_sort( $section->controls, array( 
     2565                'priority'        => 'ASC', 
     2566                'instance_number' => 'ASC', 
     2567            ) ); 
    25552568 
    25562569            if ( ! $section->panel ) { 
     
    25672580 
    25682581        // Prepare panels. 
    2569         uasort( $this->panels, array( $this, '_cmp_priority' ) ); 
     2582        $this->panels = wp_list_sort( $this->panels, array( 
     2583            'priority'        => 'ASC', 
     2584            'instance_number' => 'ASC', 
     2585        ) ); 
    25702586        $panels = array(); 
    25712587 
     
    25752591            } 
    25762592 
    2577             uasort( $panel->sections, array( $this, '_cmp_priority' ) ); 
     2593            $panel->sections = wp_list_sort( $panel->sections, array( 
     2594                'priority'        => 'ASC', 
     2595                'instance_number' => 'ASC', 
     2596            ) ); 
    25782597            $panels[ $panel->id ] = $panel; 
    25792598        } 
     
    25822601        // Sort panels and top-level sections together. 
    25832602        $this->containers = array_merge( $this->panels, $this->sections ); 
    2584         uasort( $this->containers, array( $this, '_cmp_priority' ) ); 
     2603        $this->containers = wp_list_sort( $this->containers, array( 
     2604            'priority'        => 'ASC', 
     2605            'instance_number' => 'ASC', 
     2606        ) ); 
    25852607    } 
    25862608 
  • trunk/src/wp-includes/customize/class-wp-customize-nav-menu-item-setting.php

    r38618 r38859  
    533533 
    534534        if ( ARRAY_A === $args['output'] ) { 
    535             $GLOBALS['_menu_item_sort_prop'] = $args['output_key']; 
    536             usort( $items, '_sort_nav_menu_items' ); 
     535            $items = wp_list_sort( $items, array( 
     536                $args['output_key'] => 'ASC', 
     537            ) ); 
    537538            $i = 1; 
    538539 
  • trunk/src/wp-includes/customize/class-wp-customize-nav-menu-setting.php

    r37539 r38859  
    288288        // Make sure the menu objects get re-sorted after an update/insert. 
    289289        if ( ! $is_delete && ! empty( $args['orderby'] ) ) { 
    290             $this->_current_menus_sort_orderby = $args['orderby']; 
    291             usort( $menus, array( $this, '_sort_menus_by_orderby' ) ); 
     290            $menus = wp_list_sort( $menus, array( 
     291                $args['orderby'] => 'ASC', 
     292            ) ); 
    292293        } 
    293294        // @todo add support for $args['hide_empty'] === true 
     
    314315     * 
    315316     * @since 4.3.0 
     317     * @deprecated 4.7.0 Use wp_list_sort() 
    316318     * @access protected 
     319     * 
    317320     * @param object $menu1 
    318321     * @param object $menu2 
     
    322325     */ 
    323326    protected function _sort_menus_by_orderby( $menu1, $menu2 ) { 
     327        _deprecated_function( __METHOD__, '4.7.0', 'wp_list_sort' ); 
     328 
    324329        $key = $this->_current_menus_sort_orderby; 
    325330        return strcmp( $menu1->$key, $menu2->$key ); 
  • trunk/src/wp-includes/deprecated.php

    r38785 r38859  
    37993799    return preg_replace( '%&\s*\{[^}]*(\}\s*;?|$)%', '', $string ); 
    38003800} 
     3801 
     3802/** 
     3803 * Sort categories by ID. 
     3804 * 
     3805 * Used by usort() as a callback, should not be used directly. Can actually be 
     3806 * used to sort any term object. 
     3807 * 
     3808 * @since 2.3.0 
     3809 * @deprecated 4.7.0 Use wp_list_sort() 
     3810 * @access private 
     3811 * 
     3812 * @param object $a 
     3813 * @param object $b 
     3814 * @return int 
     3815 */ 
     3816function _usort_terms_by_ID( $a, $b ) { 
     3817    _deprecated_function( __FUNCTION__, '4.7.0', 'wp_list_sort' ); 
     3818 
     3819    if ( $a->term_id > $b->term_id ) 
     3820        return 1; 
     3821    elseif ( $a->term_id < $b->term_id ) 
     3822        return -1; 
     3823    else 
     3824        return 0; 
     3825} 
     3826 
     3827/** 
     3828 * Sort categories by name. 
     3829 * 
     3830 * Used by usort() as a callback, should not be used directly. Can actually be 
     3831 * used to sort any term object. 
     3832 * 
     3833 * @since 2.3.0 
     3834 * @deprecated 4.7.0 Use wp_list_sort() 
     3835 * @access private 
     3836 * 
     3837 * @param object $a 
     3838 * @param object $b 
     3839 * @return int 
     3840 */ 
     3841function _usort_terms_by_name( $a, $b ) { 
     3842    _deprecated_function( __FUNCTION__, '4.7.0', 'wp_list_sort' ); 
     3843 
     3844    return strcmp( $a->name, $b->name ); 
     3845} 
     3846 
     3847/** 
     3848 * Sort menu items by the desired key. 
     3849 * 
     3850 * @since 3.0.0 
     3851 * @deprecated 4.7.0 Use wp_list_sort() 
     3852 * @access private 
     3853 * 
     3854 * @global string $_menu_item_sort_prop 
     3855 * 
     3856 * @param object $a The first object to compare 
     3857 * @param object $b The second object to compare 
     3858 * @return int -1, 0, or 1 if $a is considered to be respectively less than, equal to, or greater than $b. 
     3859 */ 
     3860function _sort_nav_menu_items( $a, $b ) { 
     3861    global $_menu_item_sort_prop; 
     3862 
     3863    _deprecated_function( __FUNCTION__, '4.7.0', 'wp_list_sort' ); 
     3864 
     3865    if ( empty( $_menu_item_sort_prop ) ) 
     3866        return 0; 
     3867 
     3868    if ( ! isset( $a->$_menu_item_sort_prop ) || ! isset( $b->$_menu_item_sort_prop ) ) 
     3869        return 0; 
     3870 
     3871    $_a = (int) $a->$_menu_item_sort_prop; 
     3872    $_b = (int) $b->$_menu_item_sort_prop; 
     3873 
     3874    if ( $a->$_menu_item_sort_prop == $b->$_menu_item_sort_prop ) 
     3875        return 0; 
     3876    elseif ( $_a == $a->$_menu_item_sort_prop && $_b == $b->$_menu_item_sort_prop ) 
     3877        return $_a < $_b ? -1 : 1; 
     3878    else 
     3879        return strcmp( $a->$_menu_item_sort_prop, $b->$_menu_item_sort_prop ); 
     3880} 
  • trunk/src/wp-includes/functions.php

    r38849 r38859  
    34903490 * 
    34913491 * @since 3.0.0 
     3492 * @since 4.7.0 Uses WP_List_Util class. 
    34923493 * 
    34933494 * @param array       $list     An array of objects to filter 
     
    35033504 */ 
    35043505function wp_filter_object_list( $list, $args = array(), $operator = 'and', $field = false ) { 
    3505     if ( ! is_array( $list ) ) 
     3506    if ( ! is_array( $list ) ) { 
    35063507        return array(); 
    3507  
    3508     $list = wp_list_filter( $list, $args, $operator ); 
    3509  
    3510     if ( $field ) 
    3511         $list = wp_list_pluck( $list, $field ); 
    3512  
    3513     return $list; 
     3508    } 
     3509 
     3510    $util = new WP_List_Util( $list ); 
     3511 
     3512    $util->filter( $args, $operator ); 
     3513 
     3514    if ( $field ) { 
     3515        $util->pluck( $field ); 
     3516    } 
     3517 
     3518    return $util->get_output(); 
    35143519} 
    35153520 
     
    35183523 * 
    35193524 * @since 3.1.0 
     3525 * @since 4.7.0 Uses WP_List_Util class. 
    35203526 * 
    35213527 * @param array  $list     An array of objects to filter. 
     
    35293535 */ 
    35303536function wp_list_filter( $list, $args = array(), $operator = 'AND' ) { 
    3531     if ( ! is_array( $list ) ) 
     3537    if ( ! is_array( $list ) ) { 
    35323538        return array(); 
    3533  
    3534     if ( empty( $args ) ) 
    3535         return $list; 
    3536  
    3537     $operator = strtoupper( $operator ); 
    3538     $count = count( $args ); 
    3539     $filtered = array(); 
    3540  
    3541     foreach ( $list as $key => $obj ) { 
    3542         $to_match = (array) $obj; 
    3543  
    3544         $matched = 0; 
    3545         foreach ( $args as $m_key => $m_value ) { 
    3546             if ( array_key_exists( $m_key, $to_match ) && $m_value == $to_match[ $m_key ] ) 
    3547                 $matched++; 
    3548         } 
    3549  
    3550         if ( ( 'AND' == $operator && $matched == $count ) 
    3551           || ( 'OR' == $operator && $matched > 0 ) 
    3552           || ( 'NOT' == $operator && 0 == $matched ) ) { 
    3553             $filtered[$key] = $obj; 
    3554         } 
    3555     } 
    3556  
    3557     return $filtered; 
     3539    } 
     3540 
     3541    $util = new WP_List_Util( $list ); 
     3542    return $util->filter( $args, $operator ); 
    35583543} 
    35593544 
     
    35663551 * @since 3.1.0 
    35673552 * @since 4.0.0 $index_key parameter added. 
     3553 * @since 4.7.0 Uses WP_List_Util class. 
    35683554 * 
    35693555 * @param array      $list      List of objects or arrays 
     
    35763562 */ 
    35773563function wp_list_pluck( $list, $field, $index_key = null ) { 
    3578     if ( ! $index_key ) { 
    3579         /* 
    3580          * This is simple. Could at some point wrap array_column() 
    3581          * if we knew we had an array of arrays. 
    3582          */ 
    3583         foreach ( $list as $key => $value ) { 
    3584             if ( is_object( $value ) ) { 
    3585                 $list[ $key ] = $value->$field; 
    3586             } else { 
    3587                 $list[ $key ] = $value[ $field ]; 
    3588             } 
    3589         } 
    3590         return $list; 
    3591     } 
    3592  
    3593     /* 
    3594      * When index_key is not set for a particular item, push the value 
    3595      * to the end of the stack. This is how array_column() behaves. 
    3596      */ 
    3597     $newlist = array(); 
    3598     foreach ( $list as $value ) { 
    3599         if ( is_object( $value ) ) { 
    3600             if ( isset( $value->$index_key ) ) { 
    3601                 $newlist[ $value->$index_key ] = $value->$field; 
    3602             } else { 
    3603                 $newlist[] = $value->$field; 
    3604             } 
    3605         } else { 
    3606             if ( isset( $value[ $index_key ] ) ) { 
    3607                 $newlist[ $value[ $index_key ] ] = $value[ $field ]; 
    3608             } else { 
    3609                 $newlist[] = $value[ $field ]; 
    3610             } 
    3611         } 
    3612     } 
    3613  
    3614     return $newlist; 
     3564    $util = new WP_List_Util( $list ); 
     3565    return $util->pluck( $field, $index_key ); 
     3566} 
     3567 
     3568/** 
     3569 * Sorts a list of objects, based on one or more orderby arguments. 
     3570 * 
     3571 * @since 4.7.0 
     3572 * 
     3573 * @param array        $list    An array of objects to filter. 
     3574 * @param string|array $orderby Optional. Either the field name to order by or an array 
     3575 *                              of multiple orderby fields as $orderby => $order. 
     3576 * @param string       $order   Optional. Either 'ASC' or 'DESC'. Only used if $orderby 
     3577 *                              is a string. 
     3578 * @return array The sorted array. 
     3579 */ 
     3580function wp_list_sort( $list, $orderby = array(), $order = 'ASC' ) { 
     3581    if ( ! is_array( $list ) ) { 
     3582        return array(); 
     3583    } 
     3584 
     3585    $util = new WP_List_Util( $list ); 
     3586    return $util->sort( $orderby, $order ); 
    36153587} 
    36163588 
  • trunk/src/wp-includes/link-template.php

    r38814 r38859  
    170170            $cats = get_the_category($post->ID); 
    171171            if ( $cats ) { 
    172                 usort($cats, '_usort_terms_by_ID'); // order by ID 
     172                $cats = wp_list_sort( $cats, array( 
     173                    'term_id' => 'ASC', 
     174                ) ); 
    173175 
    174176                /** 
  • trunk/src/wp-includes/nav-menu.php

    r38744 r38859  
    559559 
    560560/** 
    561  * Sort menu items by the desired key. 
    562  * 
    563  * @since 3.0.0 
    564  * @access private 
    565  * 
    566  * @global string $_menu_item_sort_prop 
    567  * 
    568  * @param object $a The first object to compare 
    569  * @param object $b The second object to compare 
    570  * @return int -1, 0, or 1 if $a is considered to be respectively less than, equal to, or greater than $b. 
    571  */ 
    572 function _sort_nav_menu_items( $a, $b ) { 
    573     global $_menu_item_sort_prop; 
    574  
    575     if ( empty( $_menu_item_sort_prop ) ) 
    576         return 0; 
    577  
    578     if ( ! isset( $a->$_menu_item_sort_prop ) || ! isset( $b->$_menu_item_sort_prop ) ) 
    579         return 0; 
    580  
    581     $_a = (int) $a->$_menu_item_sort_prop; 
    582     $_b = (int) $b->$_menu_item_sort_prop; 
    583  
    584     if ( $a->$_menu_item_sort_prop == $b->$_menu_item_sort_prop ) 
    585         return 0; 
    586     elseif ( $_a == $a->$_menu_item_sort_prop && $_b == $b->$_menu_item_sort_prop ) 
    587         return $_a < $_b ? -1 : 1; 
    588     else 
    589         return strcmp( $a->$_menu_item_sort_prop, $b->$_menu_item_sort_prop ); 
    590 } 
    591  
    592 /** 
    593561 * Return if a menu item is valid. 
    594562 * 
     
    683651 
    684652    if ( ARRAY_A == $args['output'] ) { 
    685         $GLOBALS['_menu_item_sort_prop'] = $args['output_key']; 
    686         usort($items, '_sort_nav_menu_items'); 
     653        $items = wp_list_sort( $items, array( 
     654            $args['output_key'] => 'ASC', 
     655        ) ); 
    687656        $i = 1; 
    688657        foreach ( $items as $k => $item ) { 
     
    777746                $menu_item->type_label = __( 'Post Type Archive' ); 
    778747                $post_content = wp_trim_words( $menu_item->post_content, 200 ); 
    779                 $post_type_description = '' == $post_content ? $post_type_description : $post_content;  
     748                $post_type_description = '' == $post_content ? $post_type_description : $post_content; 
    780749                $menu_item->url = get_post_type_archive_link( $menu_item->object ); 
    781750            } elseif ( 'taxonomy' == $menu_item->type ) { 
  • trunk/src/wp-settings.php

    r38832 r38859  
    9292// Load early WordPress files. 
    9393require( ABSPATH . WPINC . '/compat.php' ); 
     94require( ABSPATH . WPINC . '/class-wp-list-util.php' ); 
    9495require( ABSPATH . WPINC . '/functions.php' ); 
    9596require( ABSPATH . WPINC . '/class-wp-matchesmapregex.php' ); 
Note: See TracChangeset for help on using the changeset viewer.