LINUX.ORG.RU

[C] Функция для получения части строки ?

 


0

1

Просмотрел libc, glib и не нашёл такой функции.

Придётся писать свою ?

Нужна примерно такая :
get_middle_string ( char * string, int begin_index, int length )

И функция должна возвращать часть строки
начиная с символа с номером begin_index и
размером length, но в пределах строки.

Просто после перехода с Delphi на Линукс в нём в Libc, Glib какой-то маленький набор функций для работы со строками. Может я какую-то особую строковую библиотеку не заметил ?

xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

char *dst, *src;
int begin_index, length;
//память выделить самостоятельно

strncpy(dst, src+begin_index, length) не? :)

адресная арифметика рулит! ;) адрес+константа=адрес

aol ★★★★★
()
Ответ на: комментарий от aol

char *dst, *src; int begin_index, length; //память выделить самостоятельно

strncpy(dst, src+begin_index, length) не? :)

адресная арифметика рулит! ;) адрес+константа=адрес

aol (16.08.2010 9:46:44)

Ну тут ещё нужно сделать проверку не превышает ли begin_index размер строки (strlen).

Ну да адресная арифметика. Ну я то уже сделал свою реализацию через memcpy и memset.

Я думал что есть особая специальная функция.

xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

Ни в каком месте это костыль не напоминает.

twosev ★★
()
Ответ на: комментарий от beastie

ты это, полегше на поворотах. где ты тут костыль узрел?

beastie ** (16.08.2010 10:19:44)

«string + begin_index» это это же передача адреса, а не номера (индекса) начального символа.

xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

возможно вам будет приятнее передавать такое &string[begin_index] коли не знаете как работают с указателями

donkey3000
()
Ответ на: комментарий от snizovtsev

>Иногда полезно немного подумать, чем плодить лишние сущности.

man strndup

CONFORMING TO
       ...  strndup(), strdupa(), and strndupa() are GNU extensions.

Иногда стоит подумать головой, прежде чем всякую херню советовать.

linuxfan
()
Ответ на: комментарий от anon_666

это это же передача адреса, а не номера (индекса) начального символа.

индекс == смещение == адрес

С чего это вдруг индекс стал синонимом слова адрес ...

xcreatepixmap
() автор топика
Ответ на: комментарий от linuxfan

Иногда полезно немного подумать, чем плодить лишние сущности.

man strndup

CONFORMING TO ... strndup(), strdupa(), and strndupa() are GNU extensions.

Иногда стоит подумать головой, прежде чем всякую херню советовать.

Это потому что «GNU extensions» не POSIX, не кросплатформенно ?

xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

>Это потому что «GNU extensions» не POSIX, не кросплатформенно ?

Да

linuxfan
()
Ответ на: комментарий от enep

1)читаем вопрос
2)думаем над вопросом
3)отвечаем на вопрос

rg-400
()
Ответ на: комментарий от rg-400

Зато при работе с указателями «автоматически» смещение переводится в правильный адрес :)

Eddy_Em ☆☆☆☆☆
()
Ответ на: комментарий от true_admin

Правда, проверку begin_index < strlen все равно надо делать. А потом уже использовать, например, malloc + strncpy, если нет желания использовать strndup.

Eddy_Em ☆☆☆☆☆
()
Ответ на: комментарий от rg-400

Пожалуйста.

CL-USER> (subseq "linux.org.ru" 5)
".org.ru"
CL-USER> (subseq "linux.org.ru" 0 5)
"linux"
anonymous
()

Я не понял, часть строки это как? Выделять память под подстроку?
В Си нет GC для строк.

для остального - strlen() и memmove()

Love5an
()
Ответ на: комментарий от true_admin

Я к тому, что в дельфях имеется некий автоматический менеджмент памяти для строк, и там принят стиль соответствующий работы с ними. В Си для данной задачи корректна была бы такая функция: int subseq(const char* s, char* out, int start1, int end1, int start2, int end2);

Love5an
()

В результате у меня вышло это :

//###################################################################
char * 
get_middle_malloc ( 
    char * source_str_ch_p, 
    int begin_index_i, 
    int flag_all_length_i, 
    int middle_length_i )
//
// Когда flag_all_length_i = 1, это значит нужно скопировать всё 
// до конца строки.
//
{
    // Если пустая строка.
    if ( source_str_ch_p == NULL )
        return NULL;
       
    int source_str_length_i;
    
    source_str_length_i = strlen (source_str_ch_p);
    
    // Если строка меньше чем нужно.
    if ( begin_index_i > (source_str_length_i - 1) )
        return NULL;
    
    int end_length_i;
    
    end_length_i = source_str_length_i - begin_index_i;
    
    // Если не указан размер, то всё до конца.
    // if ( middle_length_i == -1 )
    if ( flag_all_length_i == 1 )
        middle_length_i = end_length_i;
    
    // Если до конца строки меньше нужного.
    if (middle_length_i > end_length_i)
        middle_length_i = end_length_i;
    
    char * middle_str_ch_p;
    
    middle_str_ch_p = malloc ( middle_length_i + 1 );
    
    // memset ( middle_str_ch_p, 0, (middle_length_i + 1) );
    
    memcpy ( 
        middle_str_ch_p, 
        (char *) ( (unsigned long) source_str_ch_p + begin_index_i ),
        middle_length_i
        );
    
    // Set terminated null byte.
    memset ( 
        (char *) ( (unsigned long) middle_str_ch_p + (middle_length_i - 1 + 1) ),
        0, 
        1 );
    
    return middle_str_ch_p;
    
};

//###################################################################

char * 
get_part_str_to_end_malloc ( 
    char * source_str_ch_p, 
    int begin_index_i 
    )
{
    
    return get_middle_malloc ( source_str_ch_p, begin_index_i, 1, 0 );

};

//###################################################################

char * 
get_part_str_malloc ( 
    char * source_str_ch_p, 
    int begin_index_i,
    int middle_length_i
    )
{
    
    return get_middle_malloc ( 
        source_str_ch_p, begin_index_i, 0, middle_length_i 
        );
        
};

//###################################################################
xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

чем вам не нравится запись str + index?
зачем дали такие сложные имена переменным?
читайте секцию возвращаемые значения malloc(3)

rg-400
()
Ответ на: комментарий от rg-400

чем вам не нравится запись str + index?

Я сделал функцию с проверкой возможных проблем выхода за границы переменной.

зачем дали такие сложные имена переменным?

Не сложные, а наглядные (для меня). К тому же у каждой переменной указан тип в конце. Это удобно.

читайте секцию возвращаемые значения malloc(3)

Malloc возвращает «void *». И что ?

xcreatepixmap
() автор топика
Ответ на: комментарий от xcreatepixmap

Malloc возвращает «void *». И что ?

malloc иногда возвращает значение NULL.

я бы написал так, хотя это тоже не торт.

char *  
xstrnsub(const char *str, size_t first_ind, size_t sub_size) 
{
        size_t len;
        char *sub_str;
        
        len = strlen(str);
          
        if ((sub_size == 0) || (len < (first_ind + sub_size))) {
                errno = EINVAL;
                return NULL; 
        }
    
        sub_str = (char *) malloc(sub_size + 1); 
           
        if (sub_str == NULL) {
                errno = ENOMEM;
                return NULL; 
        }
        
        memcpy(sub_str, str + first_ind, sub_size);       
        sub_str[sub_size] = '\0';    
    
        return sub_str; 
     
} char *  
xstrsub(const char *str, size_t first_ind) 
{
        size_t len;
        size_t sub_size;
        char *sub_str;
        
        len = strlen(str);
          
        if (first_ind >= len ) {
                errno = EINVAL;
                return NULL; 
        }
        
        sub_size = len - first_ind;
        
        sub_str = (char *) malloc(sub_size + 1); 
           
        if (sub_str == NULL) {
                errno = ENOMEM;
                return NULL; 
        }
        
        memcpy(sub_str, str + first_ind, sub_size);       
        sub_str[sub_size] = '\0';    
    
        return sub_str; 
     
}

rg-400
()

Арифметика, ага, адресная, х*ядресная. А потом удивляемся, почему Unicode до сих пор не получил повсеместного распространения.

man wcsdup

anonymous
()
Ответ на: комментарий от anonymous

>Unicode до сих пор не получил повсеместного распространения.

RLY?

anon_666
()
Ответ на: комментарий от anonymous

Consequently,programs that need to be portable across any C or C++ compiler should not use wchar_t for storing Unicode text.

rg-400
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.