Diskuze: Rozsah pole
V předchozím kvízu, Online test znalostí C++, jsme si ověřili nabyté zkušenosti z kurzu.
Neregistrovaný
Zobrazeno 24 zpráv z 24.
//= Settings::TRACKING_CODE_B ?> //= Settings::TRACKING_CODE ?>
V předchozím kvízu, Online test znalostí C++, jsme si ověřili nabyté zkušenosti z kurzu.
template <class T, size_t N> //N je pocet prvkov pola (velkost musi byt znma pri preklade)
void List(T (&source)[N]){
//...
}
To je blbost. To tam rovnou dám parametr pro počet prvků a vynásobím jej pak 32... Jenže je to tedy pěkně naprd - chtěl jsem to jako deklaraci Listu s n prvky. Takhlen je už jednodušší volat Add, jelikož nejen, že neexistuje zkrácená verze initializace pole, ale jak v poli, tak v parametru budu muset dávat velikost pole...
Co sa snazias naprogramovat?
Vies o tom ze malloc nevola constructory?
List<string> strings = *new List<string>(new string[3]{ ":((", ":D", "....." }, 3);
List třídu mám už dlouho, chtěl jsem jen zkrátit deklaraci, znám-li už nějaký počet prvků předem... Tohle to celé jen komplikuje - místo zjednodušení...
Jistě - jsem debil a dělám dynamické pole....
#include <initializer_list>
template <class T>
class List{
public:
template<size_t N>
List(const T (&source)[N]){
std::cout << "List sa inicializuje z pola o " << N << " prvkoch\n";
}
List(std::initializer_list<T>&& ilist){
std::cout << "List sa inicializuje z inicializer_listu o " << ilist.size() << " prvkoch\n";
}
};
int main(){
using namespace std;
List<char> list1{"string"};
List<char> list2{'a', 'b', 'c', 'd'};
return 0;
}
Pouzivas strasne vela alokacii na heape, c++ nie je java ani c#...
includy funguju rovnako ako v c, vecsina kompilatorov podporuje ale #pragma once alebo si spravys guary sam cez ifndef, define, endif.
Inak ta tvoja funkcia Add ma velku chybu, nevola sa konstruktor takze ti to v lepsom pripade bude padat alebo budu vznkat memory lake-y.
void* mem = malloc(sizeof(T)); //alokujes pamet
new(mem) T(...); //zavolas konstruktor
reinterpret_cast<T*>(mem)->~T(); //zavolas destructor
free(mem); //dealokujes pamet
Akonahle pouzivas malloc, realloc a free, tak si konstruktory a destruktory musis valoat rucne. Napr std::vector je podobne implementovany.
Ale já se ptal na to, co mám dělat s tím "std::initializer_list"...
Musis mat kompilator co podporuje c++11.
Musis includovat: <initializer_list>
A potom mozes pouzit ten priklad co som ti dal.
Nemůžu. Já používám T*. Ne list...
>g++ -W -Wall -Werror -std=gnu++11 -I ./ -o main.exe main.cpp
In file included from /usr/include/System.h:2:0,
from main.cpp:3:
/usr/include/System/Collections/Generic/List.h: In instantiation of ‘System::Collections::Generic::List<T>::List(std::initializer_list<_Tp>&&) [with T = const char*]’:
main.cpp:10:46: required from here
/usr/include/System/Collections/Generic/List.h:39:6: error: invalid conversion from ‘std::initializer_list<const char*>::const_iterator {aka const char* const*}’ to ‘const char**’ [-fpermissive]
/usr/include/System/Collections/Generic/List.h:42:10: error: initializing argument 1 of ‘void System::Collections::Generic::List<T>::Allocate(T*, int) [with T = const char*]’ [-fpermissive]
>Exit code: 1
Potřebuji z toho mít T*/[]...
Já nevím - připadám si, jako by jsi si myslel, že jsem úplně negramotný...
A cyklus jsem tam měl předtím - viz. hoře. Přijde mi zbytečné cyklit, když je to vše v požadovaném formátu - stačí T* nastavit na T*. Jediná věc byla, že jsem musel zadat jak do pole, tak do dalšího parametru velikost - je to ale lepší než cyklus zase...
Nemůžu si pomoct, ale občas mi jako negramotný připadáš
Možná by nebylo špatné, kdyby ses konečně zaregistroval. Takhle mám tendenci si z tebe dělat srandu, i když vidím, že něco přece jen umíš.
Ak to spravne chapem tak sa snazis implementovat dynamicke pole na sposob std::vector. Aby si nas zmiatol tak si ho nasval List co sa pouziva vecsinou na zretaene zoznamy. Chces implementovat konstruktor v ktorom budes moct specifikovat zoznam prvkov ktore chces mat v poly po inicializacii. Chapem to spravne?
Seznam se dá implementovat nejen zřetězením elementů, ale i pomocí pole. Přitom pole je v běžných případech o dost rychlejší.
Tvl. Je to list jako vyšitý - stejný jako v C#. (Pak udělám i slovník - jako v C# - List.Add, List.Remove, List.RemoveAt, List.Count,...) Jen jsem doteď neměl v konstruktoru možnost zadat počáteční prvky. To jsem zařídil přes pole. Nevýhodou toho ale bylo, že se nedala dynamicky zjistit velikost - a když jsem se zde zeptal, začal jsi z toho dělat kdovíco...
List(T* source)
{
count = jak?;
list = (T*)malloc(count);
*list = *source;
}
sizeof prostě nefunguje no. Tak já budu zadávat tu velikost ročně a smířím se s tím asi...
Negramotný fakt nejsem. A programuji už pár let - a to i komerčně... (Od strojáku po dotazovací jazyky + se dnes a denně hrabu v HW.)
Je zvláštní, že všechny tvé diskuze na všech fórech dopadají stejně.
Přečti si první příspěvek. Kde jsem udělal chybu?
To ze si predtym programoval v jave/c# ma hned napadlo po tom ako som zbadal toto:
List<string> strings = *new List<string>(new string[3]{ ":((", ":D", "....." }, 3);
To moje riesenie co som ti dal v na zaciatku pomocou referencie na staticke pole a incializer listu ta moholo naviest na spravne riesenie ale asi ti to moc nepomohlo. Budem taky velkoisi ze ti sem dam ukazkovy kod:
#include <initializer_list>
template <class T>
class Vector{
void* raw_data;
T* data(size_t s = 0){return reinterpret_cast<T*>(raw_data) + s;}
const T* data(size_t s = 0)const {return reinterpret_cast<const T*>(raw_data) + s;}
size_t data_size = 0;
size_t alloc_size = 0;
public:
Vector(size_t reserve = 0){
alloc_size = reserve +1;
raw_data = malloc(sizeof(T)*alloc_size);
}
~Vector(){
clear();
free(raw_data);
}
size_t size()const{return data_size;}
void clear(){
for(T* i = data(data_size-1); i >= data(); --i)
i->~T();
data_size = 0;
}
void Add(const T& x){ //prida prvok na koniec
if(data_size >= alloc_size){
alloc_size *= 2;
raw_data = realloc(raw_data, sizeof(T)*alloc_size);
}
new(data(data_size)) T(x);
++data_size;
}
void Remove(){ //odstrani prvok z konca
if(data_size){
data(--data_size)->~T();
}
}
Vector(std::initializer_list<T>&& ilist):Vector(ilist.size()){
for(const T& x: ilist)
Add(x);
}
T* begin(){return data();}
const T* begin()const{return data();}
T* end(){return data(data_size);}
const T* end()const{return data(data_size);}
};
#include <iostream>
#include <string>
int main(){
using namespace std;
Vector<string> vec{"string1", "string2", "string3"};
vec.Add("string4");
vec.Add("string5");
vec.Add("string6");
vec.Remove();
vec.Add("string7");
for(auto& str : vec)cout << str << '\n';
return 0;
}
Zobrazeno 24 zpráv z 24.