перевод UTF-8 строки в ASCII

gumlego
Offline
Зарегистрирован: 20.11.2013

Получаю символы с интернета в UTF-8 коде, символы складываются в строку. Хочу сравнить полученную строку с заданной ASCII строкой. Как перевести utf-8 код в ascii ?

if (client.connected()) {
    if (client.available()) {
      inChar = client.read();
      if ((inChar==10)||(inChar==0)||(inChar=='\n')) currentLine="";
      else currentLine+=inChar;
      if (currentLine=="  <text>") writepost;

 

maksim
Offline
Зарегистрирован: 12.02.2012

gumlego пишет:

Как перевести utf-8 код в ascii ?

Да в общем то никак. 

Одним из преимуществ является совместимость с ASCII — любые их 7-битные символы отображаются как есть. Если размер символа в кодировке UTF-8 = 1 байт. Код имеет вид (0aaa aaaa), где «0» — просто ноль, остальные биты «a» — это код символа в кодировке ASCII;

 

beervolk
Offline
Зарегистрирован: 21.11.2013

UTF8 - это возможность хранения в текстовом виде юникодных символов. Один символ может занимать 1, 2, 3, ... байта.

ourlive
Offline
Зарегистрирован: 26.05.2012

почему это utf в asc вдруг стало перевсети нельзя? Наверняка же нужно не все 65тыщ из утфа переводить. Через таблицу перевода посимвольно.

maksim
Offline
Зарегистрирован: 12.02.2012

beervolk пишет:

UTF8 - это возможность хранения в текстовом виде юникодных символов. Один символ может занимать 1, 2, 3, ... байта.

И???

ourlive пишет:

почему это utf в asc вдруг стало перевсети нельзя? Наверняка же нужно не все 65тыщ из утфа переводить. Через таблицу перевода посимвольно.

Кто сказал что нельзя? Сообщение #1 прочитайте внимательно.

Для непонятливых или невнимательно читающих перевожу что написано в посте #1. В стандартной таблице ASCII 128 символов, все они соответсятвуют символам UTF-8 длинной 1 байт. То есть, все то что не карказяба и есть символ ASCII. 

Что вы тут собрались переводить???

Едиственное что можно сделать при "переводе" это отсеивать карказябы, проверяя старший бит.

 

gumlego
Offline
Зарегистрирован: 20.11.2013

maksim пишет:

beervolk пишет:

UTF8 - это возможность хранения в текстовом виде юникодных символов. Один символ может занимать 1, 2, 3, ... байта.

И???

ourlive пишет:

почему это utf в asc вдруг стало перевсети нельзя? Наверняка же нужно не все 65тыщ из утфа переводить. Через таблицу перевода посимвольно.

Кто сказал что нельзя? Сообщение #1 прочитайте внимательно.

Для непонятливых или невнимательно читающих перевожу что написано в посте #1. В стандартной таблице ASCII 128 символов, все они соответсятвуют символам UTF-8 длинной 1 байт. То есть, все то что не карказяба и есть символ ASCII. 

Что вы тут собрались переводить???

Едиственное что можно сделать при "переводе" это отсеивать карказябы, проверяя старший бит.

 

А как по-другому сравнивать 2 строки разных кодировок?

maksim
Offline
Зарегистрирован: 12.02.2012

Так как есть так и сравнивайте. В чем проблема то? В строку попадают карказябы? Ну добавьте еще одно условие и будите получать куски строк без карказяб:

    if ((inChar&0x80)||(inChar==10)||(inChar==0)||(inChar=='\n')) currentLine="";

или при сборки строки игнорируйте карказябы:

    else if (!(inChar&0x80)) currentLine+=inChar;

 

gumlego
Offline
Зарегистрирован: 20.11.2013

он не находит такую строку, также как и любые символы в utf-8

maksim
Offline
Зарегистрирован: 12.02.2012

Кто он? И как вы это определяете?

gumlego
Offline
Зарегистрирован: 20.11.2013

Программа не находит эту строчку, хотя она там есть, также программа не находит любые словосочетания, которые есть в тексте. Так как полученный текст в коде utf-8, а то что я ввожу в среду программирования «processing» в коде ascii, я предложил, что надо как то перевести полученный текст из utf-8 в ASCII, поэтому и создал эту тему.

maksim
Offline
Зарегистрирован: 12.02.2012

Так как вы определяете что она там есть?

Что выводит:

if (client.connected()) {
    if (client.available()) {
      inChar = client.read();
      print(inChar);

 

gumlego
Offline
Зарегистрирован: 20.11.2013

посимвольно выводит все хорошо

maksim
Offline
Зарегистрирован: 12.02.2012

Карказябы встречаются?

maksim
Offline
Зарегистрирован: 12.02.2012

А так выводится ваша строка?

if (client.connected()) {
    if (client.available()) {
      inChar = client.read();
      if ((inChar==10)||(inChar==0)||(inChar=='\n')) 
      {
         print(currentLine);
         currentLine="";
      }
      else currentLine+=inChar;

 

gumlego
Offline
Зарегистрирован: 20.11.2013

построчно тоже все выводится.
Кракозябр нет

maksim
Offline
Зарегистрирован: 12.02.2012

Значит не верно задаете строку для сравнения.

maksim
Offline
Зарегистрирован: 12.02.2012

Кстати, 10 это и есть '\n',еще стоит отсеивать перевод каретки 

if ((inChar=='\0')||(inChar=='\n')||(inChar=='\r')) currentLine="";

А сравнения производить только после сборки строки:

if ((inChar == '\0')||(inChar == '\n')||(inChar == '\r'))
{
  print(currentLine);
  if (currentLine == "  <text>") writepost;
  currentLine="";
}
else currentLine+=inChar;

 

gumlego
Offline
Зарегистрирован: 20.11.2013

Строка имеет вид " <«text»>нужный мне текст<«text»>" без « и »
Вроде я догадался в чем проблема.
Браузер выводит строки с пробелами для удобного чтения конструции html.
Скорее всего, arduino выводит без пробелов, я не зафиксировал этот момент во время посимвольного вывода. Дома посмотрю, отпишусь.

maksim
Offline
Зарегистрирован: 12.02.2012

Это и есть не верно задать строку для сравнения. Копируйте ее прям из консоли в код.

ourlive
Offline
Зарегистрирован: 26.05.2012

А зачем так сложно перебором фильтровать спецсимволы? Всё что ниже пробела char(32), всё спецсимволы.

А ещё почитайте это. Иначе подозреваю вы начнёте винить компилятор в невозможности проверки эквивалентности строк.  Похоже нужно создавать и закреплять в топике пост "принципиальные различия arduino и processing". Или "стандартные ошибки".

gumlego
Offline
Зарегистрирован: 20.11.2013

Увы, проблема не связана с пробелами. Статья не помогла.

Вот весь код: 

#include <SPI.h>
#include <Ethernet.h>


// Введите MAC-адрес и IP-адрес вашего контроллера
// IP-адрес должен соответствовать вашей локальной сети
byte mac[] = {
  0x00, 0xAA, 0xBB, 0xCC, 0xDE, 0x01 };
IPAddress ip(192,168,0,118); //<<< IP-АДРЕС ВВОДИТЬ СЮДА!!!
 
// инициализации экземпляра библиотеки:
EthernetClient client;
// задержка между запросами
const int requestInterval = 10000;
// URL сервера, которому будем отправлять запросы
char serverName[] = "api.vk.com";
// сделан ли запрос после подключения
boolean requested;
// время в милисекундах с последнего подключения к серверу
long lastAttemptTime = 0;
// ID пользователя 
String UserID = "40874228";
// строка для сохранения текста с сервера
String currentLine = "";
char inChar;
String mytext = "  <text>";

 
void writepost()
{
  while (inChar!='<')
  {
    inChar = client.read();
    Serial.print(inChar);
  }
}

void setup() {
 // резервируем место для строки:
  currentLine.reserve(256);
 
  // инициализация последовательного порта:
  Serial.begin(9600);
  // попытка подключения с DHCP:
  if (!Ethernet.begin(mac)) {
    // если DHCP-сервер отсутствует в сети,
    // подключаемся с заданным нами IP-адресом:
    Ethernet.begin(mac, ip);
  }
  // подключаемся к Серверу:
  connectToServer();
}
 
void loop()
{
  if (client.connected()) {
    if (client.available()) {
      // считываем полученные байты:
      inChar = client.read();
      //Serial.print(inChar);
      if ((inChar==10)||(inChar==0)||(inChar=='\n')) {currentLine="";}
      else currentLine+=inChar;
      if (currentLine.equals(mytext) == true) writepost;
    }
  }
  else if (millis() - lastAttemptTime > requestInterval) {
    // если мы в данный момент не подключены к серверу
    // и прошло 2 минуты с момента последнего подключения, пробуем
    // подключится снова и прочитать последний опубликованный твит:
    connectToServer();
  }
}
 

// функция подключения к серверу
void connectToServer() {
 
  Serial.println("connecting to server...");
  if (client.connect(serverName, 80)) {
    Serial.println("making HTTP request...");
  // Создаем GET HTTP-запрос:
    client.println("GET /method/wall.get.xml?owner_id=" + UserID + "&domain=" + UserID + "&count=1&type=post HTTP/1.1");
    client.println("HOST: api.VK.com");
    client.println("Connection: close");
    client.println();
  }
  // записываем в переменную время текущей попытки соединения:
  lastAttemptTime = millis();
}

 

В принятом тексте есть строка: "  <text>Test</text>" в этом вы можете убедиться тут.

По идее должно вывести: "Test", но ничего не выводится. Что думаете?

ourlive
Offline
Зарегистрирован: 26.05.2012

  строка63:

if (currentLine.equals(mytext) == true) {writepost;} else {print(currentLine.length());print("_");print(currentLine);print("_");println(mytext.length());}

внимательно смотрите, что у вас происходит пошагово, кстати, а без фигурных скобок if работает? да и функцию со скобками правильее вызывать.

maksim
Offline
Зарегистрирован: 12.02.2012

Дорогой вы наш человек, в чем пишите то? Вы Процессинг от Ардуино отличаете? Это код для дуины.

#include <SPI.h>
#include <Ethernet.h>


// Введите MAC-адрес и IP-адрес вашего контроллера
// IP-адрес должен соответствовать вашей локальной сети
byte mac[] = {
  0x00, 0xAA, 0xBB, 0xCC, 0xDE, 0x01 };
IPAddress ip(192,168,0,118); //<<< IP-АДРЕС ВВОДИТЬ СЮДА!!!

// инициализации экземпляра библиотеки:
EthernetClient client;
// задержка между запросами
const int requestInterval = 10000;
// URL сервера, которому будем отправлять запросы
char serverName[] = "api.vk.com";
// сделан ли запрос после подключения
boolean requested;
// время в милисекундах с последнего подключения к серверу
long lastAttemptTime = 0;
// ID пользователя 
String UserID = "40874228";
// строка для сохранения текста с сервера
String currentLine = "";
String mytext = "text";

bool tag = 0;

void writepost()
{
  char inChar = client.read();
  while (inChar != '<')
  {
    Serial.write(inChar);
    inChar = client.read();
  }
}

void setup() {
  // резервируем место для строки:
  currentLine.reserve(256);

  // инициализация последовательного порта:
  Serial.begin(9600);
  // попытка подключения с DHCP:
  if (!Ethernet.begin(mac)) {
    // если DHCP-сервер отсутствует в сети,
    // подключаемся с заданным нами IP-адресом:
    Ethernet.begin(mac, ip);
  }
  // подключаемся к Серверу:
  connectToServer();
}

void loop()
{
  if (client.connected()) 
  {
    if (client.available()) 
    {
      // считываем полученные байты:
      char inChar = client.read();
      //Serial.print(inChar);
      if (inChar == '<') tag = 1;
      else if (inChar == '>') 
      {
        tag = 0;
        if (currentLine == "text") writepost();
        currentLine="";
      }
      
      if (tag) currentLine += inChar;
    }
  }
  else if (millis() - lastAttemptTime > requestInterval) {
    // если мы в данный момент не подключены к серверу
    // и прошло 2 минуты с момента последнего подключения, пробуем
    // подключится снова и прочитать последний опубликованный твит:
    connectToServer();
  }
}


// функция подключения к серверу
void connectToServer() {

  Serial.println("connecting to server...");
  if (client.connect(serverName, 80)) {
    Serial.println("making HTTP request...");
    // Создаем GET HTTP-запрос:
    client.println("GET /method/wall.get.xml?owner_id=" + UserID + "&domain=" + UserID + "&count=1&type=post HTTP/1.1");
    client.println("HOST: api.VK.com");
    client.println("Connection: close");
    client.println();
  }
  // записываем в переменную время текущей попытки соединения:
  lastAttemptTime = millis();
}

 

gumlego
Offline
Зарегистрирован: 20.11.2013

Ошибка в вызове функции writepost.

Не разобрался где именно, просто вместо функции вставил ее содержание.

Заработало! Всем спасибо за помощь! =)

gumlego
Offline
Зарегистрирован: 20.11.2013

Я думал код для ардуины и есть processing

step962
Offline
Зарегистрирован: 23.05.2011

gumlego пишет:

Я думал код для ардуины и есть processing

Тогда уж Wiring...