Что такое и зачем нужны uint32_t , int64_t , uint8_t и тд?
Когда все начинали изучать С++ работали с разными типами данных ( char , int , std::string , bool ).Но на разных архитектурах и разные компиляторы хотят от int разное количество памяти.
Давайте рассмотрим это подробнее:
Влияние архитектуры на размер int
16-битные архитектуры:
На старых 16-битных системах тип int обычно занимал 2 байта (16 бит).
32-битные архитектуры:
На большинстве современных 32-битных систем тип int занимает 4 байта (32 бита). Это связано с тем, что 32-битные процессоры оптимально работают с данными размером 4 байта.
64-битные архитектуры:
На большинстве современных 64-битных систем тип int также занимает 4 байта (32 бита), несмотря на то, что процессоры способны работать с данными большего размера. Это сделано для обеспечения обратной совместимости и эффективности.
Мы можем сделать вывод что на разных устройствах код будет работать по разному.Но что если мы хотим чтобы наша программа работала одинаково на разных компиляторах и архитектурах?
Кроссплатформенность - способность программного обеспечения работать с несколькими аппаратными платформами или операционными системами.
Для того чтобы решить вопрос кроссплатформенности в С++ добавили Целочисленные типы фиксированной ширины.Они имеют один размер не зависимо от архитектуры.
Основные 8:
int8_t - char ( 1 байт)
int16_t - short ( 2 байта )
int32_t - int ( 4 байта )
int64_t - long long ( 8 байт )
Если добавить символ u в начале то будут unsigned типы ( которые не могут быть меньше нуля но хранят в два раза больше положительных чисел).
Все эти типы будут выделять на этапе компиляции столько битов,сколько написано в названии.
Когда все начинали изучать С++ работали с разными типами данных ( char , int , std::string , bool ).Но на разных архитектурах и разные компиляторы хотят от int разное количество памяти.
Давайте рассмотрим это подробнее:
Влияние архитектуры на размер int
16-битные архитектуры:
На старых 16-битных системах тип int обычно занимал 2 байта (16 бит).
32-битные архитектуры:
На большинстве современных 32-битных систем тип int занимает 4 байта (32 бита). Это связано с тем, что 32-битные процессоры оптимально работают с данными размером 4 байта.
64-битные архитектуры:
На большинстве современных 64-битных систем тип int также занимает 4 байта (32 бита), несмотря на то, что процессоры способны работать с данными большего размера. Это сделано для обеспечения обратной совместимости и эффективности.
Мы можем сделать вывод что на разных устройствах код будет работать по разному.Но что если мы хотим чтобы наша программа работала одинаково на разных компиляторах и архитектурах?
Кроссплатформенность - способность программного обеспечения работать с несколькими аппаратными платформами или операционными системами.
Для того чтобы решить вопрос кроссплатформенности в С++ добавили Целочисленные типы фиксированной ширины.Они имеют один размер не зависимо от архитектуры.
Основные 8:
int8_t - char ( 1 байт)
int16_t - short ( 2 байта )
int32_t - int ( 4 байта )
int64_t - long long ( 8 байт )
Если добавить символ u в начале то будут unsigned типы ( которые не могут быть меньше нуля но хранят в два раза больше положительных чисел).
Все эти типы будут выделять на этапе компиляции столько битов,сколько написано в названии.
Docs
Стандартные типы
Дополнительные сведения: Стандартные типы
Что такое ссылка (reference)
Во первых в отличии от указателя ссылка это не объект , это всего лишь альтернативное имя для объекта.
Ссылка всегда должна быть инициализирована (ПРИМ1), так как она связана всего лишь с одним объектом за все свое существование.Когда мы объявляем ссылку вместо того чтобы копировать значение мы связываем ссылку с его инициализатором.
Пример:
referenceValue имеет все свойства переменной value, может изменять ее значение так как являеться псевдонимом value.
Но есть ограничение, нельзя создавать массив ссылок(не ссылку на масив).Но можно сделать референс на массив(нужно знать размер массива на который будем ссылаться)
Пример:
Из хабра:
В C++ к массивом применяется правило, называемое сведением (decay, array-to-pointer decay). (Для перевода термина «decay» еще используется слово «низведение», также можно встретить «разложение».) Суть сведения заключается в том, что почти в любом контексте идентификатор массива преобразуется к указателю на первый элемент и информация о размере теряется. Сведение происходит и при использовании массивов в качестве параметров функций.
Функция не может возвращать массив, а вот ссылку на массив может. Без использования псевдонимов объявление такой функции выглядит несколько пугающе:
Также можно использовать ссылки для аргументов и возращения значение в функциях,в качестве члена класса,для итерации по контейнерам в for(range-based loop) и не только.
(ПРИМ1): Только если ссылка помечена как extern (она обьявлена в другом файле) то ее можно (нужно) не инициализировать.
Если будет много реакций сделаю пост про иное использование ссылок ( + что такое rvalue & lvalue reference)
#cpp #lvalue
Во первых в отличии от указателя ссылка это не объект , это всего лишь альтернативное имя для объекта.
Ссылка всегда должна быть инициализирована (ПРИМ1), так как она связана всего лишь с одним объектом за все свое существование.Когда мы объявляем ссылку вместо того чтобы копировать значение мы связываем ссылку с его инициализатором.
Пример:
int value = 256;
int& referenceValue = value; //referenceValue теперь связан с value (псевдоним value)
referenceValue имеет все свойства переменной value, может изменять ее значение так как являеться псевдонимом value.
Но есть ограничение, нельзя создавать массив ссылок(не ссылку на масив).Но можно сделать референс на массив(нужно знать размер массива на который будем ссылаться)
Пример:
int main(){
int arr[10]{};
int (&r)[10]{arr};
r[2] = 12;
std::cout<<arr[2]<<std::endl; //В консоле будет число 12
}
Из хабра:
В C++ к массивом применяется правило, называемое сведением (decay, array-to-pointer decay). (Для перевода термина «decay» еще используется слово «низведение», также можно встретить «разложение».) Суть сведения заключается в том, что почти в любом контексте идентификатор массива преобразуется к указателю на первый элемент и информация о размере теряется. Сведение происходит и при использовании массивов в качестве параметров функций.
void Foo(int a[4]);
void Foo(int a[]);
void Foo(int *a);
Функция не может возвращать массив, а вот ссылку на массив может. Без использования псевдонимов объявление такой функции выглядит несколько пугающе:
int(&Foo(int x))[4];
Также можно использовать ссылки для аргументов и возращения значение в функциях,в качестве члена класса,для итерации по контейнерам в for(range-based loop) и не только.
(ПРИМ1): Только если ссылка помечена как extern (она обьявлена в другом файле) то ее можно (нужно) не инициализировать.
Если будет много реакций сделаю пост про иное использование ссылок ( + что такое rvalue & lvalue reference)
#cpp #lvalue
Хабр
Ссылки и ссылочные типы в C++
Продолжаем серию «C++, копаем вглубь». Цель этой серии — рассказать максимально подробно о разных особенностях языка, возможно довольно специальных. Это пятая статья из серии, список предыдущих статей...
Впервые за 40 лет С++ поднялся настолько высоко,а С настолько низко
https://www.tiobe.com/tiobe-index/
https://www.tiobe.com/tiobe-index/
#include <iostream>
class A{
public:
A(){std::cout<<"A";}
};
class B{
public:
B(){std::cout<<"B";}
};
class C{
private:
B b;
A a;
public:
C() : a(),b(){ }
};
int main(){
C c;
}
#Cpp
Список инициализации конструктора
Основная задача конструктора это инициализация (P.S НЕ СТАТИЧЕСКИХ) полей класса.
Это можно сделать разными способами, присвоением в теле конструктора:
Или с помощью списка инициализации:
В конкретно этом примере, не будет никакой разницы.Но что если у нас будет переменной-членом константа или ссылка?
Как вы знаете константам как и ссылкам не может быть присвоено значение после определения , так же они должны быть иницилизированы в момент их создания.
Рассмотрим клас A c константным полем:
Получаем ошибку так как константам нельзя присвоить значение после определения.
Но что делать если нам нужно добавить ссылку или константу в наш класс?
Для решения этой проблемы добавили member initializer list.C помощью него мы можем инициализировать константные поля класса(+ ссылки) значениями непосредственно перед выполнением тела конструктора.
Теперь рассмотрим класс B с константым полем:
Все работает и поле
Также хочу отметить одну особенность такой формы инициализации полей - инициализация объектов в классе происходит не в порядке member init list а в том порядке, в котором они объявлены в классе.То есть от перестановки выражений a(_a), b(_b) и c(_c) порядок инициализации не поменяется.Сначала получит значение а , потом b , и только в конце c.
Именно поэтому в прошлом посте ответ BA
P.S хочу отметить что список иниц полей важен не только для ссылок и констант, если в классе поля-объекта нету default конструктора то мы также получим ошибку как и со вторым примером класса А.
Основная задача конструктора это инициализация (P.S НЕ СТАТИЧЕСКИХ) полей класса.
Это можно сделать разными способами, присвоением в теле конструктора:
class A{
public:
A(const int & _a, const double &_b){
a = _a;
b = _b;
}
private:
int a;
double b;
};
Или с помощью списка инициализации:
class B{
public:
B(const int &_a, const double &_b): a(_a),b(_b){}
private:
int a;
double b;
};
В конкретно этом примере, не будет никакой разницы.Но что если у нас будет переменной-членом константа или ссылка?
Как вы знаете константам как и ссылкам не может быть присвоено значение после определения , так же они должны быть иницилизированы в момент их создания.
Рассмотрим клас A c константным полем:
class A{
public:
A(const int & _a, const double &_b , const int &_c){
a = _a;
b = _b;
c = _c; //expression must be a modifiable lvalue
}
private:
int a;
double b;
const int c;
};
Получаем ошибку так как константам нельзя присвоить значение после определения.
Но что делать если нам нужно добавить ссылку или константу в наш класс?
Для решения этой проблемы добавили member initializer list.C помощью него мы можем инициализировать константные поля класса(+ ссылки) значениями непосредственно перед выполнением тела конструктора.
Теперь рассмотрим класс B с константым полем:
class B{
public:
B(const int & _a, const double &_b , const int &_c): a(_a), b(_b), c(_c) {}
private:
int a;
double b;
const int c;
};
Все работает и поле
с
наделено значением с параметра _с
.Также хочу отметить одну особенность такой формы инициализации полей - инициализация объектов в классе происходит не в порядке member init list а в том порядке, в котором они объявлены в классе.То есть от перестановки выражений a(_a), b(_b) и c(_c) порядок инициализации не поменяется.Сначала получит значение а , потом b , и только в конце c.
Именно поэтому в прошлом посте ответ BA
P.S хочу отметить что список иниц полей важен не только для ссылок и констант, если в классе поля-объекта нету default конструктора то мы также получим ошибку как и со вторым примером класса А.
Французские ученые создали нейросеть, которая лучше всех пишет код
Она обошла GPT-4o и LLAMA-3 на Python, Java, C++ и других языках.
Нейросеть от Mistral отлично подходит для математических расчетов и проектирования программ. ИИ точно выполняет все команды и быстро выдает результат.
Вот ссылка
Она обошла GPT-4o и LLAMA-3 на Python, Java, C++ и других языках.
Нейросеть от Mistral отлично подходит для математических расчетов и проектирования программ. ИИ точно выполняет все команды и быстро выдает результат.
Вот ссылка
Когда мы используем пространство имен ( namespace ) мы хотим организовать наш код в группы во избежания конфликтов имен. Пример:
Мы можем использовать одно и то же имя для переменной i.
Но иногда, это может становиться очень долгой и кропотливой работой каждый раз при обьявлении переменной или функции использовать оператор :: (оператор разрешения области видимости / scope resolution operator) для получения нужного нам типа.На редите я нашел вот такое:
Именно для таких случаев создали объявления using (using declaration) , псевдонимы пространства имен (namespace aliases) и typedef.
namespace aliases и typedef имеют одинаковую семантику , они создают синонимы/псевдонимы(aliases) , альтернативные имена для типов (смотреть ПРИМ).Это полезно для сокращения длинных имен пространств, особенно когда они вложены.В то время как using declaration , просто делает имя доступным напрямую в локальной области.
Пример:
Теперь наш Type может напрямую использоваться в пространстве имен где мы их написали.Важно отметить что при использования typedef с шаблонами могут появится трудности, а вот с namespace aliases - нет,aliases в таких случаях может быть проще и читабельнее.ПРИМ: Отличие typedef и namespace aliases - typedef работает только с типами, а не с пространствами имен.
namespace A{
int i = 3;
}
namespace B{
int i = 1;
}
void foo(){
A::i = 53;
B::i = 12;
}
Мы можем использовать одно и то же имя для переменной i.
Но иногда, это может становиться очень долгой и кропотливой работой каждый раз при обьявлении переменной или функции использовать оператор :: (оператор разрешения области видимости / scope resolution operator) для получения нужного нам типа.На редите я нашел вот такое:
LibBar::GadgetHelpers::SomeGadgimathing foobar(LibBar::GadgetHelpers::SomeGadget<type> gadget,LibBar::GadgetHelpers::GadgimathingOptions options);
Именно для таких случаев создали объявления using (using declaration) , псевдонимы пространства имен (namespace aliases) и typedef.
namespace aliases и typedef имеют одинаковую семантику , они создают синонимы/псевдонимы(aliases) , альтернативные имена для типов (смотреть ПРИМ).Это полезно для сокращения длинных имен пространств, особенно когда они вложены.В то время как using declaration , просто делает имя доступным напрямую в локальной области.
Пример:
namespace A{
namespace B{
namespace C{
class Type;
}
}
}
using A::B::C::Type; // <- using declaration
using Type = A::B::C::Type;// <- namespace aliases
typedef A::B::C::Type Type;// <- typedef
Теперь наш Type может напрямую использоваться в пространстве имен где мы их написали.Важно отметить что при использования typedef с шаблонами могут появится трудности, а вот с namespace aliases - нет,aliases в таких случаях может быть проще и читабельнее.ПРИМ: Отличие typedef и namespace aliases - typedef работает только с типами, а не с пространствами имен.
Супер интересная задача на перебор‼️‼️:
https://codeforces.com/contest/1985/problem/E
Вечером выложу решение
https://codeforces.com/contest/1985/problem/E
Вечером выложу решение
Решение с объяснением:
#include <iostream>
#include <vector>
using namespace std;
//вспомогательная функция рассчитывает кол-во различных мест внутри ящика
long long counter(const vector<long long>& v,const vector<long long>& rv){
long long result{};
if(v == rv) // если наш куб равен размеру ящика,то он вмещаеться только один раз
return 1;
for(long long i = v[1];i<=rv[1];++i){ // идем по длине
result+=rv[0] - v[0] + 1; // каждую ширину в результат
}
int z = rv[2] - v[2] + 1; // высота
return result*z;
}
int main(){
int t;cin>>t;
vector<long long> result;
for(int d = 0;d<t;++d){
long long x,y,z,S;cin>>x>>y>>z>>S;
long long maxValue{};
for(long long a = 1;a<=x;++a){
for(long long b = 1;b<=y;++b){
long long c = S/(a*b); // можно сделать цикл от 1 до z - не проходит по рантайму
// так как будут повторы a и b
if(z>=c){ // если с не выходит за пределы
if(a*b*c == S ){ // если объем равен k ( в моем случае S)
long long temp = counter({a,b,c},{x,y,z}); // создаю переменную
// для хранения расчетов;
// альтернативы:
/*
1. создать переменную в условии if
2. вызвать counter в присвоении и if
функция будет вызываться по два раза
*/
if(temp > maxValue)
maxValue = temp;
}
}
}
}
result.push_back(maxValue); // вносим в наш вектор наибольшее значение,
// если такого не нашлось - выводим ноль
}
for(const auto& i: result){ // вывод
cout<<i<<endl;
}
}
Репозиторий который кратко описывает нововведения в 11/14/17/20 стандартах.
Ссылка: https://github.com/AnthonyCalandra/modern-cpp-features
Ссылка: https://github.com/AnthonyCalandra/modern-cpp-features
GitHub
GitHub - AnthonyCalandra/modern-cpp-features: A cheatsheet of modern C++ language and library features.
A cheatsheet of modern C++ language and library features. - AnthonyCalandra/modern-cpp-features
Предикаты
Все сталкивались либо просто знают про библиотеку algorithm, в ней есть множество шаблонных функций которые облегчают работу.Все они УНИВЕРСАЛЬНЫЕ так как в аргументы принимают не контейнер целиком и не ссылки на него, а итераторы , которые позволяют проходить объекты без особого различия между разными типами контейнеров.
Что такое предикаты?
Это функция или объект (у которого перегружен bool operator()) который имеет меньше двух параметров включительно.Предикаты бывают унарными(один параметр) и бинарными(два параметра).
Но зачем вообще давать этому отдельное название?
А дело в том, что почти все алгоритмы библиотеки STL принимают предикат последним аргументом.Мы можем возвращать что хотим (true/false) и от этого будет зависеть содержимое контейнера.Для примера возмем алгоритм sort():
Он перегружен и имеет два вида:
Имеет два параметра которые обозначают диапазон [begin,end).
Имеет три параметра первые два обозначают диапазон [begin,end), а третий - бинарный предикат.
Первыйй тип это обычная функция sort которая сортирует элементы в диапазоне в порядке возрастания.
Во втором мы можем коректировать как именно мы хотим отсортировать его.
Пример (первый с функцией, второй с лямбдой):
Вывод будет одинаковым:
Все сталкивались либо просто знают про библиотеку algorithm, в ней есть множество шаблонных функций которые облегчают работу.Все они УНИВЕРСАЛЬНЫЕ так как в аргументы принимают не контейнер целиком и не ссылки на него, а итераторы , которые позволяют проходить объекты без особого различия между разными типами контейнеров.
Что такое предикаты?
Это функция или объект (у которого перегружен bool operator()) который имеет меньше двух параметров включительно.Предикаты бывают унарными(один параметр) и бинарными(два параметра).
Но зачем вообще давать этому отдельное название?
А дело в том, что почти все алгоритмы библиотеки STL принимают предикат последним аргументом.Мы можем возвращать что хотим (true/false) и от этого будет зависеть содержимое контейнера.Для примера возмем алгоритм sort():
Он перегружен и имеет два вида:
Имеет два параметра которые обозначают диапазон [begin,end).
Имеет три параметра первые два обозначают диапазон [begin,end), а третий - бинарный предикат.
Первыйй тип это обычная функция sort которая сортирует элементы в диапазоне в порядке возрастания.
Во втором мы можем коректировать как именно мы хотим отсортировать его.
Пример (первый с функцией, второй с лямбдой):
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
bool predicate(int lhs,int rhs){
return !(lhs < rhs); // in parentheses due to precedence
}
int main(){
vector<int> v{0,512,22,54,222,10};
sort(v.begin(),v.end(),predicate);
for(const auto& i : v)
cout<<i<<" ";
}
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int main(){
vector<int> v{0,512,22,54,222,10};
sort(v.begin(),v.end(),[](int lhs,int rhs){
return !(lhs < rhs);
});
for(const auto& i : v)
cout<<i<<" ";
}
Вывод будет одинаковым:
512 222 54 22 10 0
Агрегаты
Struct и class,два ключевых слова для создания собственных типов.Для использования подходит любой, единственное отличие class от struct так это изначальный модификатор доступа (public - struct ; private - class)
И так, класс считаеться агрегатом только если:
1. Имеет публичный конструктор который помечен как default(C++11) либо без аргументов.
2. Все НЕСТАТИЧЕСКИЕ поля публичные.
3. Каждое поле имеет дефолтный конструктор(если это не базовый тип).
Класс может иметь сколько угодно приватных или protected методов (не конструктов) либо статических полей.
И также можеть иметь свои собственные операторы копирования - присвоения.
Возращаясь к первому абзацу вы можете сделать вывод, что зачастую (а это выбор каждого, точно также что писать первым public или private поля и методы) используют struct для создания агрегатов.
Struct и class,два ключевых слова для создания собственных типов.Для использования подходит любой, единственное отличие class от struct так это изначальный модификатор доступа (public - struct ; private - class)
И так, класс считаеться агрегатом только если:
1. Имеет публичный конструктор который помечен как default(C++11) либо без аргументов.
2. Все НЕСТАТИЧЕСКИЕ поля публичные.
3. Каждое поле имеет дефолтный конструктор(если это не базовый тип).
Класс может иметь сколько угодно приватных или protected методов (не конструктов) либо статических полей.
И также можеть иметь свои собственные операторы копирования - присвоения.
Возращаясь к первому абзацу вы можете сделать вывод, что зачастую (а это выбор каждого, точно также что писать первым public или private поля и методы) используют struct для создания агрегатов.
Meta оштрафовали на 102 миллиона долларов за хранение паролей в виде обычного текста, которые были доступны 20 000 сотрудникам компании. Выяснилось это ещё в 19 году, и с тех пор расследование продолжалось.
Хотя компания не сообщила, сколько аккаунтов пострадало, старший сотрудник facebook рассказал, что инцидент затронул до 600 миллионов паролей. Некоторые из которых хранились в легко читаемом формате на серверах компании аж с 2012 года.
Хотя компания не сообщила, сколько аккаунтов пострадало, старший сотрудник facebook рассказал, что инцидент затронул до 600 миллионов паролей. Некоторые из которых хранились в легко читаемом формате на серверах компании аж с 2012 года.
Ссылки как параметры
Функции, это одна из неотъемлемых частей C++ которою можно встретить в любом проекте.С их помощью можно избегать дублирования, делать код компактным и читаемым.Без функций невозможен полиморфизм(который есть одним из трех основных принципов обьектно-ориентированого-програмирования).Лямбды, шаблоны и тд. станут не доступными без функций.
Несколько постов назад я писал про ссылки, и большая их часть используется именно в функциях, а точнее в параметрах.
Во первых разберемся в чем отличие ссылок в параметрах от обычного by value на примере:
Как мы видим, когда мы используем обычную переменную в качестве параметра - ничего не происходит.Но когда изменяем by value на by reference(int v на int& r) значение переменной внутри main изменяется.
Но почему так происходит?
А все дело в том, что когда мы передаем в функцию по значению, то мы создаем новую копию того объекта, который внесли в аргумент(в нашем случае переменная по значению это v, а аргумент это A).Но если мы используем в параметре ссылку - мы создаем не копию объекта,а псевдоним/альтернативное имя/синоним/alias.Он не выделяет столько же памяти под новый объект.
Имеет ли ссылка память - в стандарте не указано, и на то есть веские причины.Реальный ответ: это зависит от ссылки.Она может быть представлен как обычный указатель, а может и не существовать вообще.
Вообщем используя ссылки в параметрах вы не только можете изменять значения, а и используете намного меньше места.Речь идет про объекты, которые занимают много памяти и чтобы их скопировать нужно много ресурсов, хотя зачастую нам совсем не нужно две копии объекта.
Примеры: массивы, большие строки, потоки данных, большие структуры или классы.
Если же мы говорим про дату, которая почти ничего не занимает(например int), разницы вы практически не заметите.
Но что если вам не нужно изменять значение в функции, а требуется сам объект для дальнейших вычисленний и сравнений.Не проще будет использовать константные ссылки?
Про константные ссылки следующий пост.
Функции, это одна из неотъемлемых частей C++ которою можно встретить в любом проекте.С их помощью можно избегать дублирования, делать код компактным и читаемым.Без функций невозможен полиморфизм(который есть одним из трех основных принципов обьектно-ориентированого-програмирования).Лямбды, шаблоны и тд. станут не доступными без функций.
Несколько постов назад я писал про ссылки, и большая их часть используется именно в функциях, а точнее в параметрах.
Во первых разберемся в чем отличие ссылок в параметрах от обычного by value на примере:
void value(int v){
v = 10;
}
void ref(int& r){
r = 20;
}
int main(){
int A = 100;
value(A);
cout<<A<<"\n";
ref(A);
cout<<A<<"\n";
}
Вывод:
100
20
Как мы видим, когда мы используем обычную переменную в качестве параметра - ничего не происходит.Но когда изменяем by value на by reference(int v на int& r) значение переменной внутри main изменяется.
Но почему так происходит?
А все дело в том, что когда мы передаем в функцию по значению, то мы создаем новую копию того объекта, который внесли в аргумент(в нашем случае переменная по значению это v, а аргумент это A).Но если мы используем в параметре ссылку - мы создаем не копию объекта,а псевдоним/альтернативное имя/синоним/alias.Он не выделяет столько же памяти под новый объект.
Имеет ли ссылка память - в стандарте не указано, и на то есть веские причины.Реальный ответ: это зависит от ссылки.Она может быть представлен как обычный указатель, а может и не существовать вообще.
Вообщем используя ссылки в параметрах вы не только можете изменять значения, а и используете намного меньше места.Речь идет про объекты, которые занимают много памяти и чтобы их скопировать нужно много ресурсов, хотя зачастую нам совсем не нужно две копии объекта.
Примеры: массивы, большие строки, потоки данных, большие структуры или классы.
Если же мы говорим про дату, которая почти ничего не занимает(например int), разницы вы практически не заметите.
Но что если вам не нужно изменять значение в функции, а требуется сам объект для дальнейших вычисленний и сравнений.Не проще будет использовать константные ссылки?
Про константные ссылки следующий пост.
Telegram
C++ Chanel
Что такое ссылка (reference)
Во первых в отличии от указателя ссылка это не объект , это всего лишь альтернативное имя для объекта.
Ссылка всегда должна быть инициализирована (ПРИМ1), так как она связана всего лишь с одним объектом за все свое существование.Когда…
Во первых в отличии от указателя ссылка это не объект , это всего лишь альтернативное имя для объекта.
Ссылка всегда должна быть инициализирована (ПРИМ1), так как она связана всего лишь с одним объектом за все свое существование.Когда…
This media is not supported in your browser
VIEW IN TELEGRAM
Нейросеть GeoSpy AI научилась определять точное местонахождение по фотографии изнутри дома, ориентируясь на вид из окна.
Разработчики уверяют, что при этом не используются метаданные фотографии – место определяется только по внешнему виду окружающей среды.
Разработчики уверяют, что при этом не используются метаданные фотографии – место определяется только по внешнему виду окружающей среды.
Media is too big
VIEW IN TELEGRAM
Telegram теперь сможет написать сообщение вместо вас: этим летом в чатах Telegram появится искусственный интеллект от Илона Маска
▪️Можно будет мгновенно создать свой стикер по текстовому запросу;
▪️Чтобы не читать новые сообщения в чате, можно запросить выдержку .
▪️ШИ сможет написать сообщение вместо вас – нужно только подать идею;
▪️Нейрометь сможет проводить фактчекинг сообщений по каналам;
▪️Прямо в строке поиска можно будет спросить что угодно;
▪️Чат-бот Grok будет закреплен у всех пользователей по умолчанию.
Компания xAI договорилась о партнерстве на 1 год, заявил Дуров. Телеграмм получит от xAI $300 млн, а также 50% дохода от подписок xAI, реализуемых через мессенджер.
▪️Можно будет мгновенно создать свой стикер по текстовому запросу;
▪️Чтобы не читать новые сообщения в чате, можно запросить выдержку .
▪️ШИ сможет написать сообщение вместо вас – нужно только подать идею;
▪️Нейрометь сможет проводить фактчекинг сообщений по каналам;
▪️Прямо в строке поиска можно будет спросить что угодно;
▪️Чат-бот Grok будет закреплен у всех пользователей по умолчанию.
Компания xAI договорилась о партнерстве на 1 год, заявил Дуров. Телеграмм получит от xAI $300 млн, а также 50% дохода от подписок xAI, реализуемых через мессенджер.