WP_Token_Map::from_array( array $mappings, int $key_length = 2 ): WP_Token_Map|null

In this article

Create a token map using an associative array of key/value pairs as the input.

Description

Example:

$smilies = WP_Token_Map::from_array( array(
     '8O' => '😯',
     ':(' => '🙁',
     ':)' => '🙂',
     ':?' => '😕',
  ) );

Parameters

$mappingsarrayrequired
The keys transform into the values, both are strings.
$key_lengthintoptional
Determines the group key length. Leave at the default value of 2 unless there’s an empirical reason to change it.

Default:2

Return

WP_Token_Map|null Token map, unless unable to create it.

Source

public static function from_array( array $mappings, int $key_length = 2 ): ?WP_Token_Map {
	$map             = new WP_Token_Map();
	$map->key_length = $key_length;

	// Start by grouping words.

	$groups = array();
	$shorts = array();
	foreach ( $mappings as $word => $mapping ) {
		if (
			self::MAX_LENGTH <= strlen( $word ) ||
			self::MAX_LENGTH <= strlen( $mapping )
		) {
			_doing_it_wrong(
				__METHOD__,
				sprintf(
					/* translators: 1: maximum byte length (a count) */
					__( 'Token Map tokens and substitutions must all be shorter than %1$d bytes.' ),
					self::MAX_LENGTH
				),
				'6.6.0'
			);
			return null;
		}

		$length = strlen( $word );

		if ( $key_length >= $length ) {
			$shorts[] = $word;
		} else {
			$group = substr( $word, 0, $key_length );

			if ( ! isset( $groups[ $group ] ) ) {
				$groups[ $group ] = array();
			}

			$groups[ $group ][] = array( substr( $word, $key_length ), $mapping );
		}
	}

	/*
	 * Sort the words to ensure that no smaller substring of a match masks the full match.
	 * For example, `Cap` should not match before `CapitalDifferentialD`.
	 */
	usort( $shorts, 'WP_Token_Map::longest_first_then_alphabetical' );
	foreach ( $groups as $group_key => $group ) {
		usort(
			$groups[ $group_key ],
			static function ( array $a, array $b ): int {
				return self::longest_first_then_alphabetical( $a[0], $b[0] );
			}
		);
	}

	// Finally construct the optimized lookups.

	foreach ( $shorts as $word ) {
		$map->small_words     .= str_pad( $word, $key_length + 1, "\x00", STR_PAD_RIGHT );
		$map->small_mappings[] = $mappings[ $word ];
	}

	$group_keys = array_keys( $groups );
	sort( $group_keys );

	foreach ( $group_keys as $group ) {
		$map->groups .= "{$group}\x00";

		$group_string = '';

		foreach ( $groups[ $group ] as $group_word ) {
			list( $word, $mapping ) = $group_word;

			$word_length    = pack( 'C', strlen( $word ) );
			$mapping_length = pack( 'C', strlen( $mapping ) );
			$group_string  .= "{$word_length}{$word}{$mapping_length}{$mapping}";
		}

		$map->large_words[] = $group_string;
	}

	return $map;
}

Changelog

VersionDescription
6.6.0Introduced.

User Contributed Notes

You must log in before being able to contribute a note or feedback.