Почему это появляется в моих строках С#:

У меня есть строка в С#, инициализированная следующим образом:

string strVal = "£2000";

Однако всякий раз, когда я пишу эту строку, записывается следующее:

а £ 2000

Он не делает это с долларами.

Пример бит кода, который я использую, чтобы записать значение:

System.IO.File.AppendAllText(HttpContext.Current.Server.MapPath("/logging.txt"), strVal);

Я предполагаю, что это что-то связано с локализацией, но если строки С# просто юникод наверняка, это должно сработать?

ПОДТВЕРЖДЕНИЕ: Немного больше информации, ответ Джона Скита правильный, однако я также получаю проблему, когда я URLEncode строку. Есть ли способ предотвратить это?

Итак, строка с кодировкой URL выглядит следующим образом:

"% c2% a32000"

% c2 = Â % a3 = £

Если я кодирую как ASCII, £ появляется как?

Любые идеи?

Ответ 1

Набор символов URL по умолчанию, используемый на страницах HTML и в заголовках HTTP, называется ISO-8859-1 или ISO Latin-1.

Это не то же самое, что и UTF-8, и это не то же самое, что ASCII, но он вписывается в один байт за символ. Диапазон от 0 до 127 во многом похож на ASCII, а весь диапазон от 0 до 255 совпадает с диапазоном 0000-00FF Unicode.

Итак, вы можете сгенерировать его из строки С#, отбросив каждый символ до байта, или вы можете использовать Encoding.GetEncoding("iso-8859-1"), чтобы получить объект для преобразования для вас.

(В этом наборе символов британский фунт-символ равен 163.)

Фон

В RFC говорится, что незакодированный текст должен быть ограничен традиционным 7-битным диапазоном ASCII США и всего остального (плюс специальный URL-адрес разделители) должны быть закодированы. Но он оставляет открытым вопрос о том, какой набор символов используется для верхней половины 8-битного диапазона, что делает его зависимым от контекста, в котором отображается URL.

И этот контекст определяется двумя другими стандартами: HTTP и HTML, которые задают набор символов по умолчанию и которые вместе создают практически непреодолимую силу для разработчиков, предполагая, что адресная строка содержит процентные кодировки, которые относятся к ISO- 8859-1.

ISO-8859-1 - это набор символов текстового контента, отправленного через HTTP, за исключением случаев, когда это указано иначе. Поэтому к моменту появления строки URL в заголовке HTTP GET она должна быть в ISO-8859-1.

Другим фактором является то, что HTML также использует ISO-8859-1 по умолчанию, а URL-адреса обычно возникают как ссылки на HTML-страницах. Поэтому, когда вы создаете простую минимальную HTML-страницу в "Блокноте", URL-адреса, которые вы вводите в этот файл, находятся в ISO-8859-1.

Он иногда описывается как "дыра" в стандартах, но на самом деле это не так; это просто, что HTML/HTTP заполняет пробел, оставленный RFC для URL-адресов.

Следовательно, например, совет эта страница:

URL-кодировка символа состоит из символа "%", за которым следует двухзначное шестнадцатеричное представление (без учета регистра) ISO-Latin кодовая точка для символа.

(ISO-Latin - другое имя для IS-8859-1).

Так много для теории. Вставьте это в блокнот, сохраните его как .html файл и откройте его в нескольких браузерах. Нажмите ссылку, и Google должен искать британский фунт.

<HTML>
  <BODY>
    <A href="http://www.google.com/search?q=%a3">Test</A>
  </BODY>
</HTML>

Он работает в IE, Firefox, Apple Safari, Google Chrome. У меня сейчас нет других доступных.

Ответ 2

AppendAllText выписывает текст в UTF-8.

Что вы используете, чтобы посмотреть на него? Скорее всего, это то, что не понимает UTF-8, или не пытается сначала использовать UTF-8. Скажите своему редактору/наблюдателю, что это файл UTF-8, и все должно быть хорошо. В качестве альтернативы используйте перегрузку AppendAllText, которая позволяет вам указать кодировку и использовать любую кодировку, которая будет наиболее удобной для вас.

РЕДАКТИРОВАТЬ: В ответ на ваш отредактированный вопрос причина, по которой он не работает при кодировании с ASCII, заключается в том, что E не находится в наборе символов ASCII (который является Unicode 0-127).

URL-кодирование также использует UTF-8, по внешнему виду. Опять же, если вы хотите использовать другую кодировку, укажите ее в HttpUtility.UrlEncode перегрузке, которая принимает кодировку.

Ответ 4

Я заметил, что это происходит только тогда, когда используются длинные строки (более 4000) символов. Мое решение заключалось в получении параметра в базе данных, я просто заменяю знак Â ничем. Будьте осторожны, на самом деле может понадобиться, и если это так, это решение не подходит.