Определение кодировки.

Статус
В этой теме нельзя размещать новые ответы.

trooll

PHP кодер
Регистрация
22 Дек 2008
Сообщения
482
Реакции
117
Доброго времени суток.

Вопрос такого плана, как определиться кодировку строки в частности html страницы (желательно с точностью 90%) средствами PHP.

Сразу хочу сказать что определение с помощью mb_ функций или выпарской значения тега <meta http-equiv="Content-Type" content="text/html; charset=???" /> не подходит.
 
Доброго времени суток.
Вопрос такого плана, как определиться кодировку строки в частности html страницы (желательно с точностью 90%) средствами PHP.
Сразу хочу сказать что определение с помощью mb_ функций или выпарской значения тега <meta http-equiv="Content-Type" content="text/html; charset=???" /> не подходит.

гугл уже не тру?

первый же результат:
 
гугл уже не тру?
первый же результат: *** скрытое содержание ***
Гугл как раз тру! Этим сейчас и занимаюсь.

По выше переведенному примеру:
Функция не определяет utf-8.
 
а какая вообще задача стоИт?
для какого-нить парсера я бы не заморачивался и действительно брал бы значение метатега - дешево и сердито...

и что означает "определить кодировку строки"? - т.е. вы предполагаете, что есть некий текст в котором одна строка может иметь одну кодировку, а следующая другую?

возможно поможет
 
Да вот просто и выпарсивал мета тег, но споткнулся сегодня на такой вот задачке:

Есть некий сайт:

Егошняя мета в разметки html:
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

А на самом деле кодировка страницы:
windows-1251

Скрипт выпарсивает мету и как послушный работник конвертирует из указанной кодировки в мета теге в необходимую в итоге получает сыр бор, так как на самом деле кодировка у страницы windows-1251


Идея с:

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


Зачем изобретать велосипед и пытаться определить кодировку "своими" методами?
Для просмотра ссылки Войди или Зарегистрируйся
1) Раз ТС пишет что нужно определить кодировку, значит ее именно надо определить, а не конвертировать.
2) Это не велосипед, поскольку стандартные функции в php для определения кодировки текста работают некорректно.
 
Зачем изобретать велосипед и пытаться определить кодировку "своими" методами?
http://nulled.in/showpost.php?p=1654597&postcount=8

Как правильно заметил saen кодировку необходимо именно определить, а конвертировать в необходимую это уже следующий этап который не так сложен.

Если на чистоту то дело в следующем:
Отталкиваясь от предыдущего своего поста добавлю к нему следующее. Сейчас работаю на скриптом постера (чего именно я думаю не для кого не секрет Для просмотра ссылки Войди или Зарегистрируйся), при разборе полетов скрипта собственно наткнулся на данную проблему (см. Старт пост).

Ну так почему именно необходимо именно определить кодировку? По причине того что на выходе скрипт должен сконвертить валидные данные для постинга, а точнее на данном этапе перевести данные в правильную кодировку. Ну и естественно второй момент это валидная работа с данными страницы. Можно конечно привести данные страницы к единой кодировки использую решение которое предложил B0nuse что корректно позволит работать в плане распарски и т.д. но как не крути удаленному серверу не объяснишь что ты от него хочешь подсовывая данные в непонятной кодировки.
 
В случае с кодировка устанавливается в HTTP-headers строкой:
Content-Type: text/html; charset=windows-1251
можно положится на то, что вебмастер позаботился о своих пользователях и хоть где то установил верную кодировку и парсить еще и HTTP-headers.
 
наткнулся на несколько вещей сразу

это фикс для кодировки

PHP:
// Fixes the encoding to uf8 
function fixEncoding($in_str) 
{ 
  $cur_encoding = mb_detect_encoding($in_str) ; 
  if($cur_encoding == "UTF-8" && mb_check_encoding($in_str,"UTF-8")) 
    return $in_str; 
  else 
    return utf8_encode($in_str); 
} // fixEncoding

варианты проверки
PHP:
/**
	 * Проверка данных на принадлежность классу символов ASCII
	 * Для значений null, integer, float, boolean возвращает TRUE.
	 *
	 * Массивы обходятся рекурсивно, если в хотябы одном элементе массива
	 * его значение не ASCII, возвращается FALSE.
	 *
	 * @param   array|scalar|null  $data
	 * @return  bool
	 */
	public static function is_ascii($data)
	{
		if (! ReflectionTypehint::isValid()) return false;
		if (is_array($data))
		{
			foreach ($data as $k => &$v)
			{
				if (! self::is_ascii($k) || ! self::is_ascii($v)) return false;
			}
			return true;
		}
		#if (is_string($data)) return preg_match('/^[\x00-\x7f]*$/sSX', $data);
		if (is_string($data)) return ltrim($data, "\x00..\x7f") === '';  #small speed improve
		if (is_scalar($data) || is_null($data)) return true;  #~ null, integer, float, boolean
		return false; #object or resource
	}

	/**
	 * Returns true if data is valid UTF-8 and false otherwise.
	 * Для значений null, integer, float, boolean возвращает TRUE.
	 *
	 * Массивы обходятся рекурсивно, если в хотябы одном элементе массива
	 * его значение не в кодировке UTF-8, возвращается FALSE.
	 *
	 * @link    http://www.w3.org/International/questions/qa-forms-utf-8.html
	 * @link    http://ru3.php.net/mb_detect_encoding
	 * @link    http://webtest.philigon.ru/articles/utf8/
	 * @link    http://unicode.coeurlumiere.com/
	 * @param   array|scalar|null  $data
	 * @param   bool               $is_strict  строгая проверка диапазона ASCII?
	 * @return  bool
	 */
	public static function is_utf8($data, $is_strict = true)
	{
		if (! ReflectionTypehint::isValid()) return false;
		if (is_array($data))
		{
			foreach ($data as $k => &$v)
			{
				if (! self::is_utf8($k, $is_strict) || ! self::is_utf8($v, $is_strict)) return false;
			}
			return true;
		}
		if (is_string($data))
		{
			if ($data === '') return true; #speed improve

			if ($is_strict && preg_match('/[^\x09\x0A\x0D\x20-\xBF\xC2-\xF7]/sSX', $data)) return false;

			#the fastest variant:
			if (function_exists('mb_check_encoding')) return mb_check_encoding($data, 'UTF-8');
			if (function_exists('iconv')) return @iconv('UTF-8', 'UTF-16', $data) !== false; #TODO: check work with test

			/*
            Рег. выражения имеют внутренние ограничения на длину повторов шаблонов поиска *, +, {x,y}
            равное 65536, поэтому используем preg_replace() вместо preg_match()
			*/
			$result = $is_strict ? preg_replace('/(?>' . self::$char_re . '
                                                    #| (.) # catch bad bytes
                                                   )+/sxSX', '', $data)
								 : #the current check allows only values in the range U+0 to U+10FFFF, excluding U+D800 to U+DFFF.
								 preg_replace('/\X+/suSX', '', $data); #\X is equivalent to \P{M}\p{M}*+
			if (function_exists('preg_last_error'))
			{
				if (preg_last_error() === PREG_NO_ERROR) return $result === '';
				if (preg_last_error() === PREG_BAD_UTF8_ERROR) return false;
			}
			elseif (is_string($result)) return $result === '';

			#в этом месте произошла ошибка выполнения регулярного выражения
			#проверяем ещё одним, самым медленным способом:
			return self::check($data, $is_strict);
		}
		if (is_scalar($data) || is_null($data)) return true;  #~ null, integer, float, boolean
		return false; #object or resource
	}
взято из
 
Статус
В этой теме нельзя размещать новые ответы.
Назад
Сверху