public static function compare_arrays( $value1, $value2 )
	{
		if ( count( $value1 ) != count( $value2 ) ) return false;

		$types = XBRL_Types::getInstance();

		foreach ( $value1 as $key => $value )
		{
			if ( ! isset( $value2[ $key ] ) ) return false;

			if ( $key == 'id' )
			{
				$pattern = "/^" . SchemaTypes::$ncName . "$/u";
				if ( ! preg_match( $pattern, $value, $matches ) )
				{
					$this->log()->taxonomy_validation( "context", "id attribute is not a valid NCName", array( 'id' => $value ) );
				}
				if ( ! preg_match( $pattern, $value2[ $key ], $matches ) )
				{
					$this->log()->taxonomy_validation( "context", "id attribute is not a valid NCName", array( 'id' => $value[ $key ] ) );
				}
			}

			if ( is_array( $value ) )
			{
				if ( ! is_array( $value2[ $key ] ) ) return false;

				// These arrays will represent a collection of elements (the key will be 'children') so compare them in order
				if ( ! XBRL_Equality::compare_arrays_ordinal( $value, $value2[ $key ]) )
				{
					return false;
				}

				continue;
			}
			else if ( in_array( $key, array( 'id', 'name', 'prefix', 'type' ) ) )
			{
				if ( $value != $value2[ $key ] )
				{
					return false;
				}

				continue;
			}

			// These can be attribute comparisons so if not the element value look for an attribute and get the type
			$aType = $key == 'value'
				? XBRL_Equality::xequalElementType( $types, $value1['name'], isset( $value1['prefix'] ) ? $value1['prefix'] : null )
				: XBRL_Equality::xequalAttributeType( $types, $key, isset( $value1['prefix'] ) ? $value1['prefix'] : null );

			$bType = $key == 'value'
				? XBRL_Equality::xequalElementType( $types, $value2['name'], isset( $value2['prefix'] ) ? $value2['prefix'] : null )
				: XBRL_Equality::xequalAttributeType( $types, $key, isset( $value2['prefix'] ) ? $value2['prefix'] : null );

			if ( ! XBRL_Equality::xequal( $value, $value2[ $key ], $aType, $bType, $types ) )
			{
				return false;
			}

		}

		return true;
	}