РЕДАКТИРОВАНИЕ ФАЙЛА
аааа="ааааа"
bbbb="bbbbbbb"
cccc="ccc"
нужно в определенной строке заменить параметр после знака = на другой. вопрос в том, что делать, если новый параметр больше или меньше чем текущий? в первом случае - затираеться следующая строка, во втором - остается мусор... посоветуйте способ покрасивше...
P. S. используються стандартные функции С, и вообще - программа должна быть написана на С, а не на С++
есть конфигурационный файл вида
аааа="ааааа"
bbbb="bbbbbbb"
cccc="ccc"
нужно в определенной строке заменить параметр после знака = на другой. вопрос в том, что делать, если новый параметр больше или меньше чем текущий? в первом случае - затираеться следующая строка, во втором - остается мусор... посоветуйте способ покрасивше...
P. S. используються стандартные функции С, и вообще - программа должна быть написана на С, а не на С++
Самый правильный способ - это заново переписывать весь файл.
Самый правильный способ - это заново переписывать весь файл.
спасибо. я уже пришел к аналогичному решению:
файл считывается построчно, затем анализируется, нужная строка меняется, потом файл перезаписывается. меня только беспокоит, насколько это эффективно... если файл - размером строк так на 2000, а в моем варианте получаеться куча malloc'ов / realloc'ов...
спасибо. я уже пришел к аналогичному решению:
файл считывается построчно, затем анализируется, нужная строка меняется, потом файл перезаписывается. меня только беспокоит, насколько это эффективно... если файл - размером строк так на 2000, а в моем варианте получаеться куча malloc'ов / realloc'ов...
Честно говоря, не понимаю зачем тут malloc/realloc.
Схема должна быть предельна проса:
ФАЙЛ -> МОДЕЛЬ -> ФАЙЛ
Т.е. на основе данных из файла строится модель данных, как дерево, граф или список, яркий пример XML DOM. А потом эта модель сохраняется обратно в файл, что-то типа Serialize.
Честно говоря, не понимаю зачем тут malloc/realloc.
Схема должна быть предельна проса:
ФАЙЛ -> МОДЕЛЬ -> ФАЙЛ
Т.е. на основе данных из файла строится модель данных, как дерево, граф или список, яркий пример XML DOM. А потом эта модель сохраняется обратно в файл, что-то типа Serialize.
ну я считываю файл в массив срок вернее массив указателей на char:
char* buffer[SIZE];
fgets - считывает i-тую строку из файла, в буффер char tmp[SOME_SIZE] затем malloc'ом выделяться нужное количество памяти:
buffer=(char*) malloc(strlen(tmp)+1);
strcpy(buffer,tmp);
вот типа того...
ну я считываю файл в массив срок вернее массив указателей на char:
char* buffer[SIZE];
fgets - считывает i-тую строку из файла, в буффер char tmp[SOME_SIZE] затем malloc'ом выделяться нужное количество памяти:
buffer=(char*) malloc(strlen(tmp)+1);
strcpy(buffer,tmp);
вот типа того...
Я сейчас как обычно все усложню. :D
Создай класс
{
private:
unsigned int m_ID; // это не обязательно
std::string m_Name;
public:
std::string m_Value;
CParam(char* name, char* val) :m_Name(name), m_Value(val) {}
CParam(char* param_line); // для создания прямо из строки файла
std::string& GetParamLine(); // получение строки параметра
bool GetParamLine(char buff, size_t size); // получение строки параметра
bool Serialize(FILE*); // для непосредственной записи в файл
};
Теперь представь простоту использования:
{
private:
std::string m_FileName;
std::list<CStringParam*> m_Params;
public:
CConfig(char* filename) :m_FileName(filename) {}
~CConfig();
bool Open(); // для открытия и считывания файла конф.
bool Save(); // для записи файла конфигурации
};
CConfig::~CConfig()
{
for(it = m_Params.begine(); it != m_Params.end(); delete *it++);
}
bool CConfig::Open()
{
fopen();
....................
while(EOF)
{
fgets(...);
CStringParam* p = new CStringParam(param_line);
m_Params.push_back(p);
}
....................
fclose();
}
bool CConfig::Save()
{
pFile = fopen(...);
....................
for(it = m_Params.begine(); it != m_Params.end(); it++)
{
(*it)->Serialize(pFile);
}
....................
fclose(pFile);
}
Думаю метода доступа к различным параметрам по имени ты и сам придумаешь.
Вместо std::list можно использовать std::map, и если специфика параметров несложная, тогда можно обойтись вообще одним классом CConfig
{
private:
std::string m_FileName;
public:
std::map<string, string> m_Params;
CConfig(char* filename) :m_FileName(filename) {}
bool Open(); // для открытия и считывания файла конф.
bool Save(); // для записи файла конфигурации
};
bool CConfig::Open()
{
fopen();
....................
while(EOF)
{
fgets(...);
// определяем название параметра
name
// определяем значение параметра
value
m_Params[name] = value;
}
....................
fclose();
}
bool CConfig::Save()
{
fopen();
....................
for(it = m_Params.begine(); it != m_Params.end(); it++)
{
// имя параметра
it->first.c_str();
// значение параметра
it->second.c_str();
}
....................
fclose();
}
хотя... :)
эх... спасибо... но одно неприятное НО. программа должна быть на С... а не С++ - посему - использование классов - отпало... :(
хотя... :)
Возможно будет сложновато, но для того, чтобы реализовать объекты в C, достаточно объявить структуру с теми же данными, только следующим образом:
typedef struct tagMYCLASS
{
..
} MYCLASS, *LPMYCLASS;
void MemberFunction(LPMYCLASS lpThis, ...);
А потом вызывать функции для нужного экземпляра. Сложности возникнут только с деструкторами.