LINUX.ORG.RU

Как на С динамически выделить память для двумерного массива char


0

0

Вот небольшой код, который выделяет статически память под 2-х мерный массив char.

int n;
char v[][10]={«green»,«red»,«blue»};
for(n=0;n<3;n++)
printf(«%s\n»,v[n]);

Печатает
green
red
blue

Как сделать тоже самое, но память выделять под массив функцией malloc?
Нужно следующее
1.   Определить указатель на двумерный массив char, без выделения памяти на сам массив
2.   Выделить память под 2-х мерный массив функцией malloc
3.   Обратится к элементам массива через указатель.


Ответ на: комментарий от Absurd

>Писал я уже тысячу раз - и про substring() за O(1) и про intern-пул, и про тредовую безопасность и т.п.

А потокобезопастность она всега нужна? Каждое обращение к строке сопровождать блокировками и мьютексами с уходом в ядро??? О какой эффективности выполнения программы можно говорить, если жаба навязывает такие функции, которые нужны далеко не всегда. Вот жаба и тормозит.

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

> Вот жаба и тормозит.

ну на самом деле с теми же строками жаба работает достаточно быстро( хотя я помню в одном из холиварных топиков на ЛОР моя реализация обошла жабовскую в 20 раз ), так что тормозит скорее не она, а то что на ней пишут

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

>А потокобезопастность она всега нужна? Каждое обращение к строке сопровождать блокировками и мьютексами с уходом в ядро???

Ваш уровень компетенции не позволяет Вам вести дискуссию на эту тему. Покиньте пожалуйста тред.

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

>Ваш уровень компетенции не позволяет Вам вести дискуссию на эту тему. Покиньте пожалуйста тред.

Объясните, что же Вы понимаете под потокобезопасностью при обработке строк и как Вы их реализовываете в Линуксе без мьютексов?

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

std::string последовательность символов(что само по себе строкой не является) + методы и операторы(!) работы с ними = вот это уже строка. Один в один как в жабе. Вот в Си строк нет.

Короче хватит пукать в лужу.

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

>В Жабе это полноценный тип данных. В C++ном STL - херня какая-то, вот именно что кривая обертка на char.

Кроме безосновательной демагогии от тебя ждать нечего?

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

Это стандартная библиотека.
То есть, часть языка.
(если предъявлять подобные претензии к CL, то окажется, его как языка и нет, т.к. синтаксис и семантика перепрограммируемы)

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

>последовательность символов(что само по себе строкой не является)
Является. Это и есть, собственно, определение строки как типа данных.

std::string последовательность символов(что само по себе строкой не является)

Последовательности что в Си, что в C++ это куски памяти и статические массивы(одномерные). Это объекты(не в плане ООП), которые хранят последовательно несколько элементов подряд. std::string это отдельная структура данных, которая последовательностью в си и c++ не является. Это просто обертка над настоящими строками Си.

+ методы и операторы(!) работы с ними

Это откуда? Из книжки «ООП/C++ для чайников»?

Вот в Си строк нет.

Нет, это как раз в Си строки есть. А в C++ нет(своих).

Короче хватит пукать в лужу.

Взаимно.

Кроме безосновательной демагогии от тебя ждать нечего?

Демагогией, по-моему, ты занимаешься.

С жабой, может быть, и не стоило сравнивать, лучше хотя бы с додиезом, но в жабе литералы это хотя бы те самые строки, которые String, хоть какая-то конгруэнтность наблюдается, в отличие от.

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

>Это стандартная библиотека.

То есть, часть языка.


Библиотека не является частью языка. Она в него не встроена. Она отдельно. Она обрабатывается компилятором неотличимо от кода программиста, использующего С++. Компилятору она безразлична. Просто комплект к компилятору для удобства решения типовых задач.

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

>Библиотека не является частью языка. Она в него не встроена.
Встроена. И это в стандарте описано.

Она обрабатывается компилятором неотличимо от кода программиста, использующего С++.

А это по барабану. В коммонлиспе можно переопределить и реализовать все, что угодно(до разумных пределов, т.е. IO и т.д. нельзя, конечно, без FFI), и тем не менее, у него довольно большой стандарт, включающий множество процедур, функций, макросов и специальных операторов, и ни один человек во вменяемом виде не будет утверждать, что, например, with-open-file, или, скажем, открывающая и закрывающая скобки не являются часть языка.

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

>Бибиотека не является частью языка. Она в него не встроена. Она отдельно. Она обрабатывается компилятором неотличимо от кода программиста, использующего С++. Компилятору она безразлична. Просто комплект к компилятору для удобства решения типовых задач.

Но что это меняет? В С++ строк нет(кроме Си строк), зато они есть в стандарной библиотеке. Зачем нагружать конструкциями компилятор если это можно включить в стандартную библиотеку?

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

>Последовательности что в Си, что в C++ это куски памяти и статические массивы(одномерные). Это объекты(не в плане ООП), которые хранят последовательно несколько элементов подряд. std::string это отдельная структура данных, которая последовательностью в си и c++ не является. Это просто обертка над настоящими строками Си.

Что за бред...

Строки стали статическими массивами.
std::string стал структурой данных С++.
В С++ появились «последовательности».
std::string стал обёрткой над строками.

Смешались в кучу кони, люди...

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

>Зачем нагружать конструкциями компилятор если это можно включить в стандартную библиотеку?
А что, включенные в библиотеку функции компилятор никак не обрабатывает когда встречает? Вот натурально бред.

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

>Но что это меняет? В С++ строк нет(кроме Си строк), зато они есть в стандарной библиотеке. Зачем нагружать конструкциями компилятор если это можно включить в стандартную библиотеку?

Вот именно, что незачем строки встраивать в язык. Но кое-кто на форуме этого понять не может, ссылаясь строки в Жабах с Решётках.

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

>Что за бред...
У тебя в голове? Поздравляю, но помочь ничем не могу.

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

Ну если товарищ Love5an не может отличить скобки в синтаксисе языка от библиотек, то дискуссия с ним смысла не имеет. Желаю ему дальнейших успехов в работе с лисп-машинами.

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

>А что, включенные в библиотеку функции компилятор никак не обрабатывает когда встречает? Вот натурально бред.
Имеется ввиду констукции более высокого уровня. Где Вы тут нашли бред?

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

>Зачем нагружать конструкциями компилятор если это можно включить в стандартную библиотеку?

Поскольку много функций берут и возвращают строки в качестве параметров для них нужен бинарный протокол, как впрочем и для массивов. А за бинарный протокол отвечает компилятор.

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

>Зачем нагружать конструкциями компилятор если это можно включить в стандартную библиотеку?

Поскольку много функций берут и возвращают строки в качестве параметров для них нужен бинарный протокол, как впрочем и для массивов. А за бинарный протокол отвечает компилятор.


Теперь, спокойно и рассудительно поясните, что вы хотели этим сказать. Лично я ничего не понял. Какой ещё бинарный протокол?

Booster ★★
()

и кто-то ещё смеет утверждать, что ЛОР не торт? :)

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

Ну видишь какое дело, в коммонлиспе программируемый ридер. И на литеру '(' можно повесить совершенно отличную от исходной функцию. Вот, я специально для тебя даже целую библиотеку написал.

(cl:in-package :cl-user)

(defpackage #:parenstrings
  (:use :cl)
  (:export #:*parenstrings-readtable*))

(in-package #:parenstrings)

(defvar *parenstrings-readtable* (copy-readtable *readtable*))

(set-macro-character
  #\(
  (lambda (s c)
    (declare (ignore c))
    (with-output-to-string (out)
      (loop for c = (read-char s)
            while (char/= c #\right_parenthesis)
            do (write-char c out))))
  nil
  *parenstrings-readtable*)

(set-macro-character
  #\)
  (lambda (s c)
    (declare (ignore s c))
    (error "Unmatched close parenthesis"))
  nil
  *parenstrings-readtable*)

;;(let ((*readtable* parenstrings:*parenstrings-readtable*))
;;  (typep (read) 'string))
;;
;;(abc)
;;==> T

btw, парсер code неправильно работает, #\( и #\) видимо считает за настоящие скобки, и когда они не сматчены, подсветка не работает; пришлось заменить #\) на #\right_parenthesis

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

Лисп безусловно крут, но к чему этот холивар? Тем более, что что-то вешать на литеру '(' это слегка странно. В си тоже макросы (конечно не в пример лисповым). Тема ушла в непонятное русло, что же будет дальше?

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

>>Поскольку много функций берут и возвращают строки в качестве параметров для них нужен бинарный протокол, как впрочем и для массивов. А за бинарный протокол отвечает компилятор.

Теперь, спокойно и рассудительно поясните, что вы хотели этим сказать. Лично я ничего не понял. Какой ещё бинарный протокол?

Ты должен был понять, т.к мысль кристально ясна любому кто умеет программировать.

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

>>Поскольку много функций берут и возвращают строки в качестве параметров для них нужен бинарный протокол, как впрочем и для массивов. А за бинарный протокол отвечает компилятор.

Теперь, спокойно и рассудительно поясните, что вы хотели этим сказать. Лично я ничего не понял. Какой ещё бинарный протокол?


Ты должен был понять, т.к мысль кристально ясна любому кто умеет программировать.

Если мне кристально не ясно, значит я не программист? Офигительные умозаключения.

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

>>Ты должен был понять, т.к мысль кристально ясна любому кто умеет программировать.

Если мне кристально не ясно, значит я не программист? Офигительные умозаключения.

Я и так пишу очень пространно и многословно. www_linux_org_ru пишет еще короче.

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

>К тому, что если скобки в лиспе - атрибут языка, то и STL в С++ - тоже.
Насчёт лиспа ничего не знаю. STL не язык. У вас какие-то особые понятия.

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

Имеется ввиду, STL это часть C++

Если скобки не атрибут лиспа, приехали - тогда оказывается, CL не существует; как языка программирования, по крайней мере.

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

>Имеется ввиду, STL это часть C++
Я разве с этим спорю? Стандартная библиотека С++ это дополнительный функционал расширяющий язык.

Если скобки не атрибут лиспа, приехали - тогда оказывается, CL не существует; как языка программирования, по крайней мере.


Повторяю, на счёт лиспа ничего не знаю.

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

Интересно, а у троллей сейчас завтрак, обед или ужин? Или дополнительное ночное питание?

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

>если предъявлять подобные претензии к CL, то окажется, его как языка и нет

я всегда это подозревал )))

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

>Является. Это и есть, собственно, определение строки как типа данных.

Это ты так определил? :) Не, это не строка.

Последовательности что в Си, что в C++ это куски памяти и статические массивы(одномерные). Это объекты(не в плане ООП), которые хранят последовательно несколько элементов подряд. std::string это отдельная структура данных, которая последовательностью в си и c++ не является. Это просто обертка над настоящими строками Си.

Или у тебя каша в голове или тебе нужно научиться выражать мысли ясней.

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

Не забываем про самое существенно отличие std::string от char * — std::string хранит длину, поэтому может содержать '\0' в середине строки и дергать strlen по каждому чиху не надо.

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

Не обижай!

> Конечно, стандарт C++ называет std::string строками. Еще бы ему их так не называть. А еще стандарт C++ говорит что C++ это объектно-ориентированный язык, и даже, вроде бы, мультипарадигмальный. Но от этого C++ таким становится чтоли?

Love5an, ты зачем обижаешь плюсистов в их же треде? :)

Строки-то как раз есть де-факто. И плохо, что это - именно std::string, который имеет фундаментальные изъяны в своем дазайне. Но тогда язык был молод. Накосячили. Исправлять уже как бы поздно. Простить можно. :)

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

> мютексы с уходом в ядро это конечно сильно

Не знаю даже, смеяться или нет. Про иммутабельность анонимус, конечно, и не слышал... И про разделение двух разных задач (String и StringBuilder), наверное, тоже...

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

Хотя сдается мне, что иммутабельность плюсам особенно никак помочь не может... Неужели действительно в плюсах нужны мьютексы и блокировки, чтобы реализовать всего лишь иммутабельные строки? Да еще чтобы утечек памяти не было? Например, чтобы сделать через подсчет ссылок, блокировки нужны. Видимо, иммутабельность как средство оптимизации работает только вместе со сборщиком мусора. А последний и плюсы как бы и не дружат вовсе.

Ну что же, ничто не дается даром. Даже пресловутая гибкость плюсов.

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

Ну ты сказанул! Твоя крутая «иммутабельность» как средство «оптимизации» означает что для замены 1 символа в строке из 1 миллиона символов надо делать копию объекта с изменённым символом и удалять старый объект. Если ещё вспомнить, что строки в жабе только UTF-16, то помойка это единственное место, где место строкам из жабы и ей подобным.

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

>мютексы с уходом в ядро это конечно сильно

Мьютексы не работают с ядром? Целиком в пространстве пользователя работа ведётся? Абсолютно без системных вызовов? Расскажите подробнее, пожалуйста.

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

В С++ нельзя разделить задачи? Использовать строку без синхронизации там, где синхронизация не нужна. И только в многопоточной программе и только критические секции защищать мьютексами. Чем это хуже зоопарка жабы из String, CharBuffer, StringBuffer, StringBuilder, сборщиками мусора и прочими шедеврами производительности?

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

Пойнт был в том, что для иммутабельных типов данных ни мьютексы, ни блокировки в пользовательском коде не нужны. Вообще.

Но так не в C++! Потому что в плюсах не удается в полной мере достаточно легко и просто реализовать эти самые иммутабельные данные в многопоточной среде. В книге «Efficient C++ Performance Programming Techniques» By Dov Bulka, David Mayhew есть целая глава 12, посвященная изучению похожего вопроса, где пытаются в общем-то иммутабельные данные реализовать посредством подсчета ссылок и с помощью необходимых блокировок. Результаты неутешительные.

А «зоопарк» из String и StringBuilder говорит о том, что задачи бывают разные. Стандартный std::string - пример того, как один объект пытается сразу решить несколько задач, нарушая принцип номер 5 Стандартов программирования на Си ++ (книга Герба Саттера и Андрея Александреску): «один объект - одна задача».

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

На вопрос про мьютексы без ухода в ядро отвечают примером futex, интерфейс котрого состоит из системного вызова, то есть работы с ядром:

The kernel interface consists mainly of one multiplexing system call:

long sys_futex (void *addr1, int op, int val1, struct timespec *timeout, void *addr2, int val3)

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

И что в подробностях? Там futex_wait который вызывает sys_futex, то есть уходит в ядро так или иначе.

void lock () {
  int c;
  if ((c = cmpxchg (val, 0, 1)) != 0) {
    if (c != 2)
      c = xchg (val, 2);
    while (c != 0) {
      futex_wait (&val, 2);
      c = xchg (val, 2);
    }
  }
}

Те же самые вызовы ядра.

the Linux kernel contains a light-weight method for process synchronization. It is used in the modern thread library implementation but is also useful when used directly.

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

>Те же самые вызовы ядра.

Если Вы соизволили таки прочитать код, то Вы могли бы отметить тот ньюанс что в случае завладения футексом сходу вызова ядра не происходит. В ядро процесс уходит чтобы не жрать CPU в глухом лупе понапрасну.

ЗЫ: Я Вам уже сказал покинуть тред. Почему Вы еще тут?

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

Если бы Вы что-то знали про pthread, то знали бы, что реализация его не принципиально не отличается от реализации futex, принципы везде одинаковые. И ядро и там и там присутствует. И использование при изменении каждого символа в «потокобезопасной» строке проверки флагов с блокировкой шины является накладными расходами. Жаба=тормоза.

Рекомендую Вам покинуть тред

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

Пример с мьютексами без использования ядра по прежнему отсутсвует.

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