restructured
This commit is contained in:
parent
c495b7c47f
commit
66cefdfd63
204 changed files with 538 additions and 13662 deletions
Binary file not shown.
|
@ -1,180 +0,0 @@
|
||||||
\documentclass{article}
|
|
||||||
\usepackage[utf8x]{inputenc}
|
|
||||||
\usepackage{ucs}
|
|
||||||
\usepackage{amsmath}
|
|
||||||
\usepackage{amsfonts}
|
|
||||||
\usepackage{marvosym}
|
|
||||||
\usepackage{wasysym}
|
|
||||||
\usepackage{upgreek}
|
|
||||||
\usepackage[english,russian]{babel}
|
|
||||||
\usepackage{graphicx}
|
|
||||||
\usepackage{float}
|
|
||||||
\usepackage{textcomp}
|
|
||||||
\usepackage{hyperref}
|
|
||||||
\usepackage{geometry}
|
|
||||||
\geometry{left=2cm}
|
|
||||||
\geometry{right=1.5cm}
|
|
||||||
\geometry{top=1cm}
|
|
||||||
\geometry{bottom=2cm}
|
|
||||||
\usepackage{tikz}
|
|
||||||
\usepackage{ccaption}
|
|
||||||
\usepackage{multicol}
|
|
||||||
\usepackage{fancyvrb}
|
|
||||||
|
|
||||||
\usepackage{listings}
|
|
||||||
%\setlength{\columnsep}{1.5cm}
|
|
||||||
%\setlength{\columnseprule}{0.2pt}
|
|
||||||
|
|
||||||
\usepackage{colortbl,graphicx,tikz}
|
|
||||||
\definecolor{X}{rgb}{.5,.5,.5}
|
|
||||||
|
|
||||||
\title{ДЗ. Работа с изображениями в формате \texttt{.ppm}}
|
|
||||||
\date{}
|
|
||||||
\begin{document}
|
|
||||||
\pagenumbering{gobble}
|
|
||||||
|
|
||||||
\lstset{
|
|
||||||
language=C++, % choose the language of the code
|
|
||||||
basicstyle=\linespread{1.1}\ttfamily,
|
|
||||||
columns=fixed,
|
|
||||||
fontadjust=true,
|
|
||||||
basewidth=0.5em,
|
|
||||||
keywordstyle=\color{blue}\bfseries,
|
|
||||||
commentstyle=\color{gray},
|
|
||||||
stringstyle=\ttfamily\color{orange!50!black},
|
|
||||||
showstringspaces=false,
|
|
||||||
%numbers=false, % where to put the line-numbers
|
|
||||||
numbersep=5pt,
|
|
||||||
numberstyle=\tiny\color{black},
|
|
||||||
numberfirstline=true,
|
|
||||||
stepnumber=1, % the step between two line-numbers.
|
|
||||||
numbersep=10pt, % how far the line-numbers are from the code
|
|
||||||
backgroundcolor=\color{white}, % choose the background color. You must add \usepackage{color}
|
|
||||||
showstringspaces=false, % underline spaces within strings
|
|
||||||
captionpos=b, % sets the caption-position to bottom
|
|
||||||
breaklines=true, % sets automatic line breaking
|
|
||||||
breakatwhitespace=true, % sets if automatic breaks should only happen at whitespace
|
|
||||||
xleftmargin=.2in,
|
|
||||||
extendedchars=\true,
|
|
||||||
keepspaces = true,
|
|
||||||
}
|
|
||||||
\lstset{literate=%
|
|
||||||
*{0}{{{\color{red!20!violet}0}}}1
|
|
||||||
{1}{{{\color{red!20!violet}1}}}1
|
|
||||||
{2}{{{\color{red!20!violet}2}}}1
|
|
||||||
{3}{{{\color{red!20!violet}3}}}1
|
|
||||||
{4}{{{\color{red!20!violet}4}}}1
|
|
||||||
{5}{{{\color{red!20!violet}5}}}1
|
|
||||||
{6}{{{\color{red!20!violet}6}}}1
|
|
||||||
{7}{{{\color{red!20!violet}7}}}1
|
|
||||||
{8}{{{\color{red!20!violet}8}}}1
|
|
||||||
{9}{{{\color{red!20!violet}9}}}1
|
|
||||||
}
|
|
||||||
|
|
||||||
\title{Семинар \#1: Введение в язык C++ (для тех, кто знает C). Классные задачи.\vspace{-5ex}}\date{}\maketitle
|
|
||||||
|
|
||||||
\section*{Hello world++}
|
|
||||||
Пишем первую программу на \texttt{C++}
|
|
||||||
\begin{lstlisting}
|
|
||||||
#include <cstdio>
|
|
||||||
int main() {
|
|
||||||
printf("Hello World++\n");
|
|
||||||
}
|
|
||||||
\end{lstlisting}
|
|
||||||
Все библиотеки из языка \texttt{C} можно использовать и в языке \texttt{C++}. Только название библиотеки без \texttt{.h} на конце и с символом \texttt{c} в начале:
|
|
||||||
\begin{verbatim}
|
|
||||||
<stdio.h> -------> <cstdio>
|
|
||||||
\end{verbatim}
|
|
||||||
|
|
||||||
Для компиляции используйте компилятор \texttt{g++}. Вот так:
|
|
||||||
\begin{verbatim}
|
|
||||||
g++ helloworld.cpp
|
|
||||||
./a.out
|
|
||||||
\end{verbatim}
|
|
||||||
Или, если вы хотите установить у исполняемого файла своё имя за место \texttt{a.out}:
|
|
||||||
\begin{verbatim}
|
|
||||||
g++ -o hello helloworld.cpp
|
|
||||||
./hello
|
|
||||||
\end{verbatim}
|
|
||||||
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 1:} Скомпилируйте и запустите простейшую программу \texttt{00helloworld.cpp}.
|
|
||||||
\item \textbf{Задача 2:} Разберитесь в программе \texttt{01structnaming.cpp}. Скомпилируйте и запустите.
|
|
||||||
\end{itemize}
|
|
||||||
|
|
||||||
\section*{Тип bool}
|
|
||||||
В прошлом семестре, для хранения результатов логических операций, мы использовали целочисленные типы.\\
|
|
||||||
В языке \texttt{C++} есть встроенный тип \texttt{bool}, который может принимать 2 значения (\texttt{true} и \texttt{false}).
|
|
||||||
\begin{lstlisting}
|
|
||||||
#include <cstdio>
|
|
||||||
int main() {
|
|
||||||
bool a = true;
|
|
||||||
bool b = false;
|
|
||||||
bool c = a || b;
|
|
||||||
|
|
||||||
if (c)
|
|
||||||
printf("Yes\n");
|
|
||||||
else
|
|
||||||
printf("No\n");
|
|
||||||
}
|
|
||||||
\end{lstlisting}
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 3:} Что напечатает эта программа? Скомпилируйте её и запустите (\texttt{02bool.cpp})
|
|
||||||
\item \textbf{Задача 4:} Напишите функцию, которая будет принимать на вход целое число и возвращать \texttt{true}, если число оканчивается на \texttt{0} и \texttt{false} иначе. Вызовите эту функцию из \texttt{main}.
|
|
||||||
\end{itemize}
|
|
||||||
|
|
||||||
\newpage
|
|
||||||
\section*{Пространство имён}
|
|
||||||
\begin{lstlisting}
|
|
||||||
#include <cstdio>
|
|
||||||
// Определяем переменные, структуры, функции внутри пространства имён foo
|
|
||||||
namespace foo {
|
|
||||||
int a = 5;
|
|
||||||
int square(int x) {
|
|
||||||
return x * x;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Чтобы получить доступ к ним вне пространства имён, нужно добавить к именам foo::
|
|
||||||
int main() {
|
|
||||||
printf("%d\n", foo::a);
|
|
||||||
}
|
|
||||||
\end{lstlisting}
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 5:} Возведите \texttt{foo::a} в квадрат с помощью функции \texttt{foo::square}.
|
|
||||||
\item \textbf{Задача 6:} Создайте своё пространство имён по имени \texttt{bar} и определите в нём переменную \texttt{a = 7}. Напечатайте значение этой переменной в \texttt{main}.
|
|
||||||
\item \textbf{Задача 7:} Сделайте задание в программе \texttt{03namespace.cpp}.
|
|
||||||
\end{itemize}
|
|
||||||
|
|
||||||
\section*{Ссылки}
|
|
||||||
Ссылка -- это переменная, которая является новым именем для существующего участка памяти.
|
|
||||||
\begin{lstlisting}
|
|
||||||
#include <cstdio>
|
|
||||||
|
|
||||||
int main() {
|
|
||||||
int a = 10;
|
|
||||||
// Создадим ссылку r на переменную a
|
|
||||||
int& r = a;
|
|
||||||
// Теперь, если изменить r, то поменяется и a
|
|
||||||
r += 5;
|
|
||||||
printf("%d\n", a);
|
|
||||||
}
|
|
||||||
\end{lstlisting}
|
|
||||||
Ссылки часто используются для тех же целей, что и указатели (только со ссылкам работать удобнее).
|
|
||||||
В отличии от указателей, ссылки:
|
|
||||||
\begin{enumerate}
|
|
||||||
\item Должны всегда инициализироваться при создании
|
|
||||||
\item Не могут никуда не ссылаться (т.е. не могут равняться \texttt{NULL})
|
|
||||||
\item Их нельзя переприсвоить. При использовании оператора \texttt{=} со ссылками изменяется та переменная, на которую ссылка ссылается, а не сама ссылка.
|
|
||||||
\end{enumerate}
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 8:} Сделайте задание в файлах \texttt{04ref.cpp}, \texttt{05ref.cpp} и \texttt{06ref.cpp}.
|
|
||||||
\end{itemize}
|
|
||||||
\section*{Перегрузка функций}
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 9:} Сделайте задание в файлах \texttt{07function\_overload.cpp}, \texttt{08nulptr.cpp} и \texttt{09default\_arguments.cpp}.
|
|
||||||
\end{itemize}
|
|
||||||
\section*{Перегрузка операторов}
|
|
||||||
\begin{itemize}
|
|
||||||
\item \textbf{Задача 10:} Сделайте задание в файлах \texttt{10operator\_overload.cpp}, \texttt{11iostream.cpp} и \texttt{12iostream\_overload.cpp}.
|
|
||||||
\end{itemize}
|
|
||||||
\end{document}
|
|
|
@ -1,33 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Здравствуйте, это первый файл семестра по языку C++ (для тех, кто знаком с языком C)
|
|
||||||
|
|
||||||
Язык C++ создан на основе языка C и одним из приоритетов C++ является обратная совместимость с C
|
|
||||||
Поэтому почти любая программа на языке C будет работать и на языке C++
|
|
||||||
|
|
||||||
Однако, нужно помнить, что это разные языки. В C++ было добавлено огромное количество новых возможностей,
|
|
||||||
что сделало C++ возможно самым объёмным и мощным языком программирования.
|
|
||||||
|
|
||||||
C++ содержит в себе во много раз больше всего, чем язык C и пройти его за один семестр не представляется возможным,
|
|
||||||
но мы пройдём ключевые части этого языка.
|
|
||||||
|
|
||||||
|
|
||||||
Для компиляции программ на C++ будем использовать компилятор g++.
|
|
||||||
Скомпилируйте эту программу вот так:
|
|
||||||
g++ 00hello.cpp
|
|
||||||
|
|
||||||
И запустите вот так (для Windows):
|
|
||||||
a.exe
|
|
||||||
|
|
||||||
И запустите вот так (для Linux):
|
|
||||||
./a.out
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("Hello World of C++\n");
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,48 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Пространства имён - namespace
|
|
||||||
|
|
||||||
Определяем переменные/структуры/функции внутри пространства имён.
|
|
||||||
Давайте назовём его mipt
|
|
||||||
|
|
||||||
Чтобы получить доступ к этим переменным/структурам/функциям
|
|
||||||
вне пространства имён, нужно добавить к имени название пространства имён и оператор ::
|
|
||||||
В данном случае нужно добавить mipt::
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
namespace mipt
|
|
||||||
{
|
|
||||||
int a = 5;
|
|
||||||
float b = 1.2;
|
|
||||||
|
|
||||||
int square(int x)
|
|
||||||
{
|
|
||||||
return x * x;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%i\n", mipt::square(4));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Скомпилируйте программу и запустите, что она напечатает?
|
|
||||||
|
|
||||||
2) Что будет, если забыть написать mipt:: у названия функции square?
|
|
||||||
|
|
||||||
3) Передайте в функцию mipt::square переменную a из пространства имён mipt
|
|
||||||
|
|
||||||
4) Напишите функцию float average(float x, float y), которая будет принимать 2 числа
|
|
||||||
и возвращать их среднее арифметическое.
|
|
||||||
Поместите эту функцию в пространство имён mipt и вызовите эту функцию из main
|
|
||||||
|
|
||||||
5) Напечатайте среднее арифметическое от a и b, используя функцию average
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,25 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
|
|
||||||
namespace mipt
|
|
||||||
{
|
|
||||||
int a = 5;
|
|
||||||
float b = 1.2;
|
|
||||||
|
|
||||||
int square(int x)
|
|
||||||
{
|
|
||||||
return x * x;
|
|
||||||
}
|
|
||||||
|
|
||||||
float average(float x, float y)
|
|
||||||
{
|
|
||||||
return (x + y) / 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%i\n", mipt::square(mipt::a));
|
|
||||||
printf("%f\n", mipt::average(mipt::a, mipt::b));
|
|
||||||
}
|
|
|
@ -1,24 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
В языке C при объявлении структуры struct Book создаётся тип по имени struct Book.
|
|
||||||
|
|
||||||
В языке C++ при объявлении структуры struct Book создаётся тип к которому
|
|
||||||
можно обращаться как по имени struct Book так и по имени Book
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[50];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
struct Book a = {"Tom Sawyer", 280, 500};
|
|
||||||
|
|
||||||
Book b = {"War and Peace", 1200, 900};
|
|
||||||
}
|
|
|
@ -1,40 +0,0 @@
|
||||||
#include <cstdio>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Определяем переменные/структуры/функции внутри пространства имён mipt
|
|
||||||
Затем к ним можно будет доступиться используя префикс mipt::
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
namespace mipt
|
|
||||||
{
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[50];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
void printBook(Book b)
|
|
||||||
{
|
|
||||||
printf("%s, pages: %d, price: %.2f\n", b.title, b.pages, b.price);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
Структура Book и функция printBook определены в пространстве имён mipt
|
|
||||||
|
|
||||||
1) Создайте переменную типа структура Book и иницилизируйте
|
|
||||||
её значениями: "War and Peace", 1200, 900
|
|
||||||
|
|
||||||
2) Напечатайте созданную переменную с помощью функции printBook
|
|
||||||
*/
|
|
|
@ -1,36 +0,0 @@
|
||||||
#include <cstdio>
|
|
||||||
|
|
||||||
|
|
||||||
namespace mipt
|
|
||||||
{
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[50];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
void printBook(Book b)
|
|
||||||
{
|
|
||||||
printf("%s, pages: %d, price: %.2f\n", b.title, b.pages, b.price);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
mipt::Book b = {"War and Peace", 1200, 900};
|
|
||||||
mipt::printBook(b);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
Структура Book и функция printBook определены в пространстве имён mipt
|
|
||||||
|
|
||||||
1) Создайте переменную типа структура Book и иницилизируйте
|
|
||||||
её значениями: "War and Peace", 1200, 900
|
|
||||||
|
|
||||||
2) Напечатайте созданную переменную с помощью функции printBook
|
|
||||||
*/
|
|
|
@ -1,60 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Зачем вообще нужны пространства имён?
|
|
||||||
|
|
||||||
Представьте, что вы создаёте большую программу, исходный код который
|
|
||||||
содержит миллионы строк кода. Конечно, большая часть кода написана не вами,
|
|
||||||
так как вы используете библиотеки, написанные другими программистами.
|
|
||||||
|
|
||||||
Библиотекой можно назвать совокупность файлов исходного кода, нацеленных
|
|
||||||
на решение какой-либо задачи. Например, есть библиотека для работы с графикой
|
|
||||||
в которой содержатся функции/структуры/классы для работы с графикой.
|
|
||||||
|
|
||||||
Если вы подключаете несколько библиотек, то существует высокая вероятность,
|
|
||||||
что название чего-либо из одной библиотеки совпадёт с названием чего-то из другой библиотеки.
|
|
||||||
Это, конечно, приведёт к ошибке.
|
|
||||||
|
|
||||||
Чтобы этого избежать и используются пространства имён.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
namespace audio
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
int calculate(int x)
|
|
||||||
{
|
|
||||||
return x + 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
namespace graphics
|
|
||||||
{
|
|
||||||
int a = 20;
|
|
||||||
|
|
||||||
int calculate(int x)
|
|
||||||
{
|
|
||||||
return x * 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%i\n", audio::a);
|
|
||||||
printf("%i\n", graphics::a);
|
|
||||||
|
|
||||||
|
|
||||||
printf("%i\n", graphics::calculate(audio::calculate(graphics::a)));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Что напечатает данная программа?
|
|
||||||
*/
|
|
|
@ -1,78 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Если вам очень не хочется постоянно писать названия пространства имён,
|
|
||||||
то вы можете использовать ключевое слово using
|
|
||||||
|
|
||||||
using namespace audio;
|
|
||||||
|
|
||||||
Это говорит о том, что начиная с этой строки audio:: перед именами писать больше не нужно
|
|
||||||
|
|
||||||
Это, конечно, полностью уничтожают всю пользу, которую приносят пространства имён.
|
|
||||||
То есть в больших проектах могут возникнуть ошибки, связанные с одинаковыми именами.
|
|
||||||
|
|
||||||
Так что так лучше не делать, а если и делать, то только в маленьких программах.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
namespace audio
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
int calculate(int x)
|
|
||||||
{
|
|
||||||
return x + 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
namespace graphics
|
|
||||||
{
|
|
||||||
int a = 20;
|
|
||||||
|
|
||||||
int calculate(int x)
|
|
||||||
{
|
|
||||||
return x * 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace network
|
|
||||||
{
|
|
||||||
int b = 20;
|
|
||||||
|
|
||||||
int solve(int x)
|
|
||||||
{
|
|
||||||
return x * 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
using namespace audio;
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%i\n", calculate(a));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Что напечатает данная программа?
|
|
||||||
|
|
||||||
2) Если заменить using namespace audio на using namespace graphics, то что напечатает программа?
|
|
||||||
|
|
||||||
3) Что если одновременно использовать пространство имён audio и пространство имён graphics?
|
|
||||||
|
|
||||||
using namespace audio;
|
|
||||||
using namespace graphics;
|
|
||||||
|
|
||||||
Приведёт ли это к ошибке и, если да, то почему?
|
|
||||||
|
|
||||||
|
|
||||||
4) Что если одновременно использовать пространство имён audio и пространство имён network?
|
|
||||||
|
|
||||||
using namespace audio;
|
|
||||||
using namespace network;
|
|
||||||
|
|
||||||
Приведёт ли это к ошибке и, если да, то почему?
|
|
||||||
*/
|
|
|
@ -1,65 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Все переменные/функции/структуры/классы стандартной библиотеки языка C++ содержатся в пространстве имён std
|
|
||||||
Рассмотрим, например, глобальную переменную cout, определённую в библиотеке iostream в пространстве имён std.
|
|
||||||
|
|
||||||
К этой переменной можно применять оператор <<
|
|
||||||
cout << объект
|
|
||||||
В результате этой операции объект напечатается на экран (если он может напечататься)
|
|
||||||
Результат оператора << также является cout, поэтому можно применять << несколько раз:
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Например это выражение: cout << "Hello " << "World" << "\n";
|
|
||||||
|
|
||||||
1) Сначала напечатается "Hello " и на место cout << "Hello " подставится cout
|
|
||||||
Получтся cout << "World" << "\n";
|
|
||||||
|
|
||||||
2) Потом напечатется "World" и на место cout << "World" подставится cout
|
|
||||||
Получтся cout << "\n";
|
|
||||||
|
|
||||||
3) В конце напечатается перенос строки
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
std::cout << "Hello World\n";
|
|
||||||
std::cout << 5 << "\n";
|
|
||||||
|
|
||||||
int x = 10;
|
|
||||||
std::cout << 5 << "\n";
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Напечатайте на экран число 1.4, используя cout (количество печатаемых знаков после запятой неважно)
|
|
||||||
Обратите внимание, что при печати с cout не нужно указывать спецификатор типа как в printf.
|
|
||||||
cout сам понимает объект какого типа ему передаётся
|
|
||||||
|
|
||||||
2) Напечатайте фразу "I am x years old", только за место x нужно подставить значение
|
|
||||||
переменной x. В данной задаче получится "I am 10 years old". Используйте cout.
|
|
||||||
|
|
||||||
3) Напечатайте на экран числа от 1 до 20, разделённые пробелом. Используйте cout
|
|
||||||
|
|
||||||
4) Вместо \n для переноса строки можно использовать endl - специальный объект из
|
|
||||||
пространства имён std.
|
|
||||||
Если мы передаём его объекту cout через оператор << то печатается перенос строки
|
|
||||||
|
|
||||||
Замените все переносы строк с \n на endl
|
|
||||||
std::cout << 5 << "\n"; --> std::cout << 5 << std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
На самом деле std::endl работает медленней, чем \n, так как он помимо печати делает flush
|
|
||||||
Поэтому, если важна скорость печати в буфер, то лучше использовать \n
|
|
||||||
|
|
||||||
|
|
||||||
5) Что будет если не написать std:: перед одним из cout?
|
|
||||||
|
|
||||||
6) Используйте using namespace std; и избавьтесь от надоедливых std:: перед cout и endl
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,16 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << 1.4 << endl;
|
|
||||||
|
|
||||||
int x = 10;
|
|
||||||
cout << "I am " << x << " years old" << endl;
|
|
||||||
|
|
||||||
for (int i = 1; i <= 20; ++i)
|
|
||||||
cout << i << " ";
|
|
||||||
cout << endl;
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,32 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
/*
|
|
||||||
В пространстве имён std очень много разных имён. Если мы добавим их всех, используя
|
|
||||||
using namespace std;
|
|
||||||
то это может привести к проблеме.
|
|
||||||
Одно из имён из std может совпасть с названием нашего объекта и это может привести к ошибке.
|
|
||||||
|
|
||||||
Так что лучше такую возможность не использовать.
|
|
||||||
|
|
||||||
Но можно добавить только одно имя так:
|
|
||||||
using std::cout;
|
|
||||||
Начиная с этого момента можно писать просто cout.
|
|
||||||
Но для всех остальных объектов из std вы должны продолжать писать std::
|
|
||||||
*/
|
|
||||||
|
|
||||||
using std::cout;
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << "Hello World" << std::endl;
|
|
||||||
cout << 5 << std::endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Добавить endl в нашу область видимости, также как и cout
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,41 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Счтиывание из стандартного входа
|
|
||||||
|
|
||||||
Рассмотрим глобальную переменную cin, определённую в библиотеке iostream в пространстве имён std.
|
|
||||||
|
|
||||||
К этой переменной можно применять оператор >>
|
|
||||||
cin >> объект
|
|
||||||
В результате этой операции объект считается с экрана (если он может быть считан)
|
|
||||||
Результат оператора >> также является cin, поэтому можно применять >> несколько раз:
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Например это выражение: cin >> a >> b;
|
|
||||||
|
|
||||||
1) Сначала считается переменная a и на место cin >> a подставится cin
|
|
||||||
Получтся cin >> b;
|
|
||||||
|
|
||||||
2) Потом считается переменная b
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a, b;
|
|
||||||
std::cin >> a >> b;
|
|
||||||
std::cout << a + b;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Что напечатает данная программа, если на вход передать числа 10 и 20?
|
|
||||||
|
|
||||||
2) Напишите программу, которая будет считывать два вещественных числа и печатать их среднее геометрическое
|
|
||||||
Функция корня sqrt есть в библиотеке <cmath>
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,10 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cmath>
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
float a, b;
|
|
||||||
std::cin >> a >> b;
|
|
||||||
std::cout << sqrt(a * b);
|
|
||||||
}
|
|
|
@ -1,42 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
#include <math.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Язык C++ обратно совместим с языком C. То есть почти любая программа на C будет работать на C++
|
|
||||||
Эта программа будет работать.
|
|
||||||
|
|
||||||
Обратите внимания, для имён, пришедших из языка C использовать std:: не обязательно
|
|
||||||
|
|
||||||
Программа работает, несмотря на то, что мы используем библиотечные
|
|
||||||
функции printf и sqrt без указания пространства имён std.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%f", sqrt(3));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Задача:
|
|
||||||
|
|
||||||
1) Что напечатает данная программа?
|
|
||||||
|
|
||||||
2) Использование библиотечных функций без std опасно, так как может привести к ошибкам,
|
|
||||||
связанных с совпадением имён. Помните, что большая программа может иметь миллионы
|
|
||||||
строк кода и совпадение ваших имен и библиотечных имён очень вероятно.
|
|
||||||
|
|
||||||
|
|
||||||
Напишите следующую функцию перед функцией main
|
|
||||||
|
|
||||||
int sqrt(int x)
|
|
||||||
{
|
|
||||||
return x + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
Что теперь напечатает программа? Объясните результат.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,37 +0,0 @@
|
||||||
#include <cstdio>
|
|
||||||
#include <cmath>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Желательно всё равно использовать std даже для имён пришедших из языка C
|
|
||||||
|
|
||||||
Также были изменены названия библиотек:
|
|
||||||
stdio.h --> cstdio
|
|
||||||
math.h --> cmath
|
|
||||||
cmath означает, что это библиотека языка C под названием math, поэтому и cmath
|
|
||||||
|
|
||||||
Они почти не отличаются от предыдущих, но при программировании на C++
|
|
||||||
желательно использовать именно эти библиотеки.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
std::printf("%f", std::sqrt(3));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Задача:
|
|
||||||
|
|
||||||
1) Что напечатает данная программа?
|
|
||||||
|
|
||||||
2) Напишите следующую функцию перед функцией main
|
|
||||||
|
|
||||||
int sqrt(int x)
|
|
||||||
{
|
|
||||||
return x + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
Что теперь напечатает программа? Объясните результат.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
|
@ -1,60 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
В C++ вводится понятие нового типа под названием Ссылка
|
|
||||||
|
|
||||||
Ссылку можно рассматривать как новое имя для объекта.
|
|
||||||
Ссылку также можно рассматривать как удобный указатель, который автоматически разыменовывается
|
|
||||||
(На самом деле под капотом ссылка и является указателем)
|
|
||||||
|
|
||||||
Ссылка объявляется с помощью значка & после имени типа.
|
|
||||||
Не стоит путать & используемый при объявлении ссылки с & используемым для нахождения адреса переменной.
|
|
||||||
Это разные &
|
|
||||||
|
|
||||||
|
|
||||||
Пусть есть переменная a
|
|
||||||
int a = 10;
|
|
||||||
Давайте создадим указатель и ссылку на эту переменную и увеличим её на 1 с помощью указателя/ссылки
|
|
||||||
|
|
||||||
Используем указатель: Используем ссылку:
|
|
||||||
int* p = &a; int& r = a;
|
|
||||||
*p += 1; r += 1;
|
|
||||||
|
|
||||||
|
|
||||||
Ссылкой пользоваться удобно, так как:
|
|
||||||
|
|
||||||
1) При создании ссылки нам не нужно передавать ей адрес
|
|
||||||
Просто передаём ей саму переменную, а ссылка уже сама находит её адрес
|
|
||||||
|
|
||||||
2) Не нужно её разыменовывать, она всегда разыменовывается сама
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
int& r = a;
|
|
||||||
r += 1;
|
|
||||||
|
|
||||||
cout << a << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Используйте ссылку r, чтобы увеличить a в 2 раза
|
|
||||||
Проверьте, как изменилась a, напечатав её
|
|
||||||
|
|
||||||
|
|
||||||
2) Используйте ссылку r, чтобы присвоить a число 100
|
|
||||||
Проверьте, как изменилась a, напечатав её
|
|
||||||
|
|
||||||
|
|
||||||
3) Создайте переменную b типа float, равную 1.5
|
|
||||||
Создайте ссылку на b и используйте эту ссылку, чтобы возвести b в квадрат
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,39 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Пусть у нас есть некоторый объект, например
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
После того как мы создали ссылку на этот объект
|
|
||||||
int& r = a;
|
|
||||||
|
|
||||||
Все (почти) операции применяемые к ссылке r применяются на самом деле к объекту a
|
|
||||||
Как будто у одного объекта теперь два имени a и r
|
|
||||||
Поэтому можно сказать, что ссылка это новое имя для объекта
|
|
||||||
|
|
||||||
При этом изменить саму ссылку (например, чтобы она начала указывать на другое имя) нельзя
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
int& r = a;
|
|
||||||
|
|
||||||
|
|
||||||
r += 5; // Прибавим к a число 5
|
|
||||||
r *= 2; // Умножим a на 2
|
|
||||||
cout << r << endl; // Напечатаем a
|
|
||||||
cout << sizeof(r) << endl; // Напечатаем размер a
|
|
||||||
cout << &r << endl; // Напечатаем адрес a
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Чему будет равно значение a в конце этой программы
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,43 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Пусть у нас есть некоторый объект, например
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
После того как мы создали ссылку на этот объект
|
|
||||||
int& r = a;
|
|
||||||
|
|
||||||
Все (почти) операции применяемые к ссылке r применяются на самом деле к объекту a
|
|
||||||
Как будто у одного объекта теперь два имени a и r
|
|
||||||
Поэтому можно сказать, что ссылка это новое имя для объекта
|
|
||||||
|
|
||||||
При этом изменить саму ссылку (например, чтобы она начала указывать на другое имя) нельзя
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a[5] = {10, 20, 30, 40, 50};
|
|
||||||
|
|
||||||
int& b = a[1];
|
|
||||||
b += 1;
|
|
||||||
|
|
||||||
for (int i = 0; i < 5; ++i)
|
|
||||||
{
|
|
||||||
cout << a[i] << " ";
|
|
||||||
}
|
|
||||||
cout << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Что будет содержать массив a в конце данной программы?
|
|
||||||
|
|
||||||
2) Создайте ссылку, которая будет указывать на последний элемент массива a
|
|
||||||
Используйте эту ссылку, чтобы умножить последний элемент массива на 2
|
|
||||||
Напечатайте этот массив
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,49 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Несмотря на то, что ссылки и указатели во многом похожи, у них есть и много больших отличий.
|
|
||||||
(помимо разной инициализации и того, что ссылку не нужно постоянно разыменовывать)
|
|
||||||
|
|
||||||
|
|
||||||
Различие 1)
|
|
||||||
Указатель можно создать без инициализации вот так:
|
|
||||||
int* p;
|
|
||||||
В этом случае в p будет храниться произвольный адрес.
|
|
||||||
Разыменовывать такой указатель, не задав его значение адресом какого-либо объекта,
|
|
||||||
очень опасно, это может привести к сложновыявляемым ошибкам.
|
|
||||||
|
|
||||||
Ссылку нельзя создать без инициализации, то есть так нельзя:
|
|
||||||
int& r;
|
|
||||||
При создании ссылки нужно указать на что она будет указывать
|
|
||||||
|
|
||||||
|
|
||||||
Различие 2)
|
|
||||||
Указатель можно приравнять нулевому значению
|
|
||||||
В C++ вводится специальное нулевое значение для указателя nullptr
|
|
||||||
Вместо NULL, который был просто равен числу 0. В C++ лучше использовать nullptr
|
|
||||||
Разыменование нулевого указателя также приведёт к ошибке.
|
|
||||||
|
|
||||||
Ссылку нельзя присвоить никакому нулевому значению
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Попробуйте создать:
|
|
||||||
a) Указатель без инициализации
|
|
||||||
б) Ссылку без инициализации
|
|
||||||
|
|
||||||
в) Указатель, равнуй нулевому значению nullptr
|
|
||||||
г) Ссылку, равную нулю
|
|
||||||
|
|
||||||
Скомпилируется ли программа в этих 4-х случаях?
|
|
||||||
*/
|
|
|
@ -1,52 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Несмотря на то, что ссылки и указатели во многом похожи, у них есть и много больших отличий.
|
|
||||||
(помимо разной инициализации и того, что ссылку не нужно постоянно разыменовывать)
|
|
||||||
|
|
||||||
|
|
||||||
Различие 3) Указатель можно переприсвоить. Если указатель сначала указывал в одно место,
|
|
||||||
например, на переменную a, то можно просто написать
|
|
||||||
p = &b;
|
|
||||||
и указатель станет указывать на переменную b.
|
|
||||||
|
|
||||||
Со ссылками такое не пройдёт, они всегда указывают на тот объект, который был указан при создании ссылки
|
|
||||||
При попытке изменить это и написать что-то вроде
|
|
||||||
r = b;
|
|
||||||
ссылка автоматически разыменуется и присваивание произойдёт к тому, на что указывала ссылка
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
int b = 20;
|
|
||||||
|
|
||||||
int* p = &a;
|
|
||||||
*p += 1;
|
|
||||||
p = &b;
|
|
||||||
*p += 1;
|
|
||||||
|
|
||||||
cout << a << " " << b << endl;
|
|
||||||
|
|
||||||
|
|
||||||
int& r = a;
|
|
||||||
r += 1;
|
|
||||||
r = b;
|
|
||||||
r += 1;
|
|
||||||
|
|
||||||
cout << a << " " << b << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Попробуйте понять, что напечатает программа без её запуска
|
|
||||||
|
|
||||||
2) Запустите программу, проверьте ваши догадки и объясните результат
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,44 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Несмотря на то, что ссылки и указатели во многом похожи, у них есть и много больших отличий.
|
|
||||||
(помимо разной инициализации и того, что ссылку не нужно постоянно разыменовывать)
|
|
||||||
|
|
||||||
Различие 4)
|
|
||||||
Арифметика указателей.
|
|
||||||
К указателю можно прибавлять/отнимать целые числа. Можно вычесть 2 указателя.
|
|
||||||
Можно применить [] к указателю. При всём этом, желательно, чтобы указатель указывал на элемент массива.
|
|
||||||
Неаккуратное использование арифметики указателей может привести к ошибкам.
|
|
||||||
Например, можно прибавить к указателю не то число и выйти за пределы массива.
|
|
||||||
|
|
||||||
|
|
||||||
Ничего такого со ссылками сделать нельзя.
|
|
||||||
При попытке прибавить к ссылке число, оно прибавится к той переменной, на которую указывает ссылка.
|
|
||||||
Так как ссылка автоматически разыменуется.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a[5] = {10, 20, 30, 40, 50};
|
|
||||||
|
|
||||||
int* p = &a[0];
|
|
||||||
|
|
||||||
p += 1; // Увеличиваем указатель
|
|
||||||
*p += 1; // Увеличиваем то, на что указывает указатель
|
|
||||||
|
|
||||||
|
|
||||||
int& r = a[0];
|
|
||||||
|
|
||||||
r += 1; // Увеличиваем то, на что указывает ссылка (она автоматически разыменовывается)
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Чему будет равен массив a в конце данной программы
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,46 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Несмотря на то, что ссылки и указатели во многом похожи, у них есть и много больших отличий.
|
|
||||||
|
|
||||||
Различие 5)
|
|
||||||
Ссылки это не совсем обычный объект, некоторые операции с ними запрещены:
|
|
||||||
|
|
||||||
Ссылку нельзя сделать элементом массива
|
|
||||||
|
|
||||||
Нельзя получить адрес ссылки (если применим & то вернётся адрес того объекта на который указывет ссылка)
|
|
||||||
Нельзя создать укатель на ссылку
|
|
||||||
Нельзя создать ссылку на ссылку
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
int x = 1;
|
|
||||||
int y = 2;
|
|
||||||
int z = 2;
|
|
||||||
|
|
||||||
int& a[3] = {x, y, z}; // Ошибка, создать массив из ссылок не получится
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Можно ли инициализировать ссылку на int простым числом вот так:
|
|
||||||
int& r = 5;
|
|
||||||
|
|
||||||
|
|
||||||
2) Ссылку на ссылку создать нельзя, но код ниже почему-то работает.
|
|
||||||
Объясните почему этот код работает
|
|
||||||
|
|
||||||
int a = 10;
|
|
||||||
int& r1 = a;
|
|
||||||
int& r2 = r1;
|
|
||||||
|
|
||||||
r2 += 1;
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,69 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
В 90% случаях ссылки используются для того чтобы передать что либо в функцию
|
|
||||||
Часто нам хочется передать переменную в функцию и изменить её там (внутри функции)
|
|
||||||
Это можно делать и с помощью указателей, но с помощью ссылок это делать гораздо удобней
|
|
||||||
Рассмотрим два эквивалентных участка кода:
|
|
||||||
|
|
||||||
Передаём по указателю: Передаём по ссылке:
|
|
||||||
|
|
||||||
void sqr(int* p) void sqr(int& r)
|
|
||||||
{ {
|
|
||||||
*p = *p * *p; r = r * r;
|
|
||||||
} }
|
|
||||||
|
|
||||||
int main() int main()
|
|
||||||
{ {
|
|
||||||
int a = 5; int a = 5;
|
|
||||||
sqr(&a); sqr(a);
|
|
||||||
cout << a << endl; cout << a << endl;
|
|
||||||
} }
|
|
||||||
|
|
||||||
|
|
||||||
Обратите внимание на 2 вещи:
|
|
||||||
1) Ссылку не нужно разыменовывать внутри функции, это происходит автоматически
|
|
||||||
|
|
||||||
2) При передаче в функцию, не нужно передавать адрес переменной
|
|
||||||
Нужно передать саму переменную, компилятор сам вычислит её адрес
|
|
||||||
|
|
||||||
При этом копирования объекта a в функцию не происходит,
|
|
||||||
ссылки работают также быстро как и указатели
|
|
||||||
*/
|
|
||||||
|
|
||||||
void sqr(int& r)
|
|
||||||
{
|
|
||||||
r = r * r;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 5;
|
|
||||||
sqr(a);
|
|
||||||
|
|
||||||
cout << a << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Напишите функцию void inc(int& x), которая должна принимать объект типа int
|
|
||||||
и увеличивать его на 1
|
|
||||||
Вызовите эту функцию из main и протестируйте её работу
|
|
||||||
|
|
||||||
2) Напишите функцию void normalize(float& x, float& y), которая должна принимать
|
|
||||||
2 объекта типа float и нормализировать их. То есть делить их на некоторое число,
|
|
||||||
так чтобы было x*x + y*y == 1
|
|
||||||
|
|
||||||
Для этого x и y нужно разделить на sqrt(x*x + y*y)
|
|
||||||
|
|
||||||
|
|
||||||
3) Можно ли передать в функцию sqr не переменную, а число?
|
|
||||||
То есть, можно ли написать так:
|
|
||||||
sqr(5)
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,50 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cmath>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
void inc(int& x)
|
|
||||||
{
|
|
||||||
x += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void normalize(float& x, float& y)
|
|
||||||
{
|
|
||||||
float norm = std::sqrt(x * x + y * y);
|
|
||||||
x /= norm;
|
|
||||||
y /= norm;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 5;
|
|
||||||
inc(a);
|
|
||||||
cout << a << endl;
|
|
||||||
|
|
||||||
float x = 9, y = 6;
|
|
||||||
normalize(x, y);
|
|
||||||
cout << x << " " << y << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Напишите функцию void inc(int& x), которая должна принимать объект типа int
|
|
||||||
и увеличивать его на 1
|
|
||||||
Вызовите эту функцию из main и протестируйте её работу
|
|
||||||
|
|
||||||
2) Напишите функцию void normalize(float& x, float& y), которая должна принимать
|
|
||||||
2 объекта типа float и нормализировать их. То есть делить их на некоторое число,
|
|
||||||
так чтобы было x*x + y*y == 1
|
|
||||||
|
|
||||||
Для этого x и y нужно разделить на sqrt(x*x + y*y)
|
|
||||||
|
|
||||||
|
|
||||||
3) Можно ли передать в функцию sqr не переменную, а число?
|
|
||||||
То есть, можно ли написать так:
|
|
||||||
sqr(5)
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,81 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Чаще всего по ссылке в функцию передаются объекты структур и классов
|
|
||||||
|
|
||||||
Даже если мы не хотим менять объект внутри функции, мы всё-равно можем
|
|
||||||
захотеть передать его по ссылке, так как передача по ссылке не копирует объект,
|
|
||||||
следовательно это гораздо более эффективно
|
|
||||||
|
|
||||||
В этом случае передаём по константной ссылке (по аналогии с константным указателем)
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[100];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
void increasePrice(Book& b, float value)
|
|
||||||
{
|
|
||||||
b.price += value;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printBook(Book& b)
|
|
||||||
{
|
|
||||||
cout << b.title << ", pages = " << b.pages << ", price = " << b.price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Book b = {"War and Peace", 1200, 900};
|
|
||||||
|
|
||||||
printBook(b);
|
|
||||||
increasePrice(b, 100);
|
|
||||||
printBook(b);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
// Тот же самый код с использованием указателей выглядел бы так:
|
|
||||||
|
|
||||||
void increasePrice(Book* b, float value)
|
|
||||||
{
|
|
||||||
b->price += value;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printBook(const Book* b)
|
|
||||||
{
|
|
||||||
cout << b->title << ", pages = " << b->pages << ", price = " << b->price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Book b = {"War and Peace", 1200, 900};
|
|
||||||
|
|
||||||
printBook(&b);
|
|
||||||
increasePrice(b, 100);
|
|
||||||
printBook(&b);
|
|
||||||
}
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Напишите функцию addPage, которая бы принимала структуру Book по ссылке
|
|
||||||
и увеличивала количество страниц на 1
|
|
||||||
Протестируйте эту функцию в main
|
|
||||||
|
|
||||||
2) Напишите функцию changeFirstLetter, которая бы принимала структуру Book по ссылке
|
|
||||||
и изменяла первую букву в названии на букву A
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,41 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[100];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
void addPage(Book& b)
|
|
||||||
{
|
|
||||||
b.pages++;
|
|
||||||
}
|
|
||||||
|
|
||||||
void changeFirstLetter(Book& b)
|
|
||||||
{
|
|
||||||
b.title[0] = 'A';
|
|
||||||
}
|
|
||||||
|
|
||||||
void printBook(const Book& b)
|
|
||||||
{
|
|
||||||
cout << b.title << ", pages = " << b.pages << ", price = " << b.price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Book b = {"War and Peace", 1200, 900};
|
|
||||||
|
|
||||||
printBook(b);
|
|
||||||
|
|
||||||
addPage(b);
|
|
||||||
printBook(b);
|
|
||||||
|
|
||||||
changeFirstLetter(b);
|
|
||||||
printBook(b);
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,73 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Ссылки, как и указатели используются для передачи объектов в функции
|
|
||||||
|
|
||||||
Рассмотрим три функции
|
|
||||||
|
|
||||||
incByValue - принимаем объект по значению
|
|
||||||
В этом случае объект копируется и функция работает с копией
|
|
||||||
|
|
||||||
incByPointer - принимаем объект по адресу
|
|
||||||
В этом случае внутри функции создаётся указатель, и в этот указатель
|
|
||||||
мы передаём адрес нашего объекта
|
|
||||||
|
|
||||||
incByReference - принимаем объект по ссылке
|
|
||||||
В этом случае происходит всё примерно то же самое, что и в случае incByPointer
|
|
||||||
Только с гораздо более приятным синтаксисом
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
void incByValue(int a)
|
|
||||||
{
|
|
||||||
a += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void incByPointer(int* p)
|
|
||||||
{
|
|
||||||
*p += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void incByReference(int& a)
|
|
||||||
{
|
|
||||||
a += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
cout << "1) Initial a = " << a << endl
|
|
||||||
|
|
||||||
incByValue(a);
|
|
||||||
cout << "2) After incByValue a = " << a << endl;
|
|
||||||
|
|
||||||
incByPointer(&a);
|
|
||||||
cout << "3) After incByPointer a = " << a << endl
|
|
||||||
|
|
||||||
incByReference(a);
|
|
||||||
cout << "4) After incByReference a = " << a << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Напишите функции:
|
|
||||||
|
|
||||||
cubeByPointer(int* p) - принимет число по указателю и возводит это число в куб
|
|
||||||
cubeByReference(int& a) - принимет число по ссылке и возводит это число в куб
|
|
||||||
|
|
||||||
Протестируйте эти функции в main
|
|
||||||
|
|
||||||
|
|
||||||
2) Написать функции:
|
|
||||||
|
|
||||||
swapByPointer(int* pa, int* pb) - принимает 2 числа по указателю и обменивает их значения
|
|
||||||
swap(int& pa, int& pb) - принимает 2 числа по ссылке и обменивает их значения
|
|
||||||
|
|
||||||
Протестируйте эти функции в main
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,54 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
void cubeByPointer(int* p)
|
|
||||||
{
|
|
||||||
*p = *p * *p * *p;
|
|
||||||
}
|
|
||||||
|
|
||||||
void cubeByReference(int& a)
|
|
||||||
{
|
|
||||||
a = a * a * a;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void swapByPointer(int* pa, int* pb)
|
|
||||||
{
|
|
||||||
int temp = *pa;
|
|
||||||
*pa = *pb;
|
|
||||||
*pb = temp;
|
|
||||||
}
|
|
||||||
|
|
||||||
void swapByReference(int& a, int& b)
|
|
||||||
{
|
|
||||||
int temp = a;
|
|
||||||
a = b;
|
|
||||||
b = temp;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 5;
|
|
||||||
cubeByPointer(&a);
|
|
||||||
cout << a << endl;
|
|
||||||
|
|
||||||
a = 5;
|
|
||||||
cubeByReference(a);
|
|
||||||
cout << a << endl;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int x = 10, y = 20;
|
|
||||||
swapByPointer(&x, &y);
|
|
||||||
cout << x << " " << y << endl;
|
|
||||||
|
|
||||||
|
|
||||||
x = 10;
|
|
||||||
y = 20;
|
|
||||||
swapByReference(x, y);
|
|
||||||
cout << x << " " << y << endl;
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,97 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cmath>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Константные ссылки можно создать, используя ключевое слово const
|
|
||||||
|
|
||||||
int a = 10;
|
|
||||||
const int& r = a;
|
|
||||||
|
|
||||||
Это означает, что a нельзя будет изменить по этой ссылке
|
|
||||||
То есть поменять a, используя ссылку r будет нельзя:
|
|
||||||
r += 1; // Ошибка!
|
|
||||||
a += 1; // OK
|
|
||||||
|
|
||||||
|
|
||||||
Важным неочевидным отличием константных ссылок от обычных ссылок является то, что обычные ссылки
|
|
||||||
можно инициализировать только объектами, которые уже храняться в памяти (например, переменными).
|
|
||||||
|
|
||||||
int& r1 = a; // OK
|
|
||||||
int& r2 = 5; // Ошибка
|
|
||||||
|
|
||||||
Константные ссылки можно инициализировать чем угодно (нужно только чтобы тип совпадал)
|
|
||||||
|
|
||||||
const int& cr1 = a; // OK
|
|
||||||
const int& cr2 = 5; // OK
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
const int& r = a;
|
|
||||||
|
|
||||||
|
|
||||||
int& r1 = 20; // Это не будет компилироваться
|
|
||||||
const int& r2 = 20 // Тут всё ОК
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Можно ли инициализировать ссылку таким образом?
|
|
||||||
float& r = std::sqrt(2);
|
|
||||||
|
|
||||||
Можно ли инициализировать константную ссылку таким образом?
|
|
||||||
const float& r = std::sqrt(2);
|
|
||||||
|
|
||||||
|
|
||||||
2) Пусть есть функция:
|
|
||||||
|
|
||||||
void printAgeV(int x)
|
|
||||||
{
|
|
||||||
cout << "My age is " << x << " years" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
int a = 10;
|
|
||||||
printAgeV(a)
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
printAgeV(20)
|
|
||||||
|
|
||||||
|
|
||||||
3) Пусть есть функция:
|
|
||||||
|
|
||||||
void printAgeR(int& x)
|
|
||||||
{
|
|
||||||
cout << "My age is " << x << " years" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
int a = 10;
|
|
||||||
printAgeR(a)
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
printAgeR(20)
|
|
||||||
|
|
||||||
|
|
||||||
4) Пусть есть функция:
|
|
||||||
|
|
||||||
void printAgeCR(const int& x)
|
|
||||||
{
|
|
||||||
cout << "My age is " << x << " years" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
int a = 10;
|
|
||||||
printAgeCR(a)
|
|
||||||
|
|
||||||
Можно ли вызвать её так?
|
|
||||||
printAgeCR(20)
|
|
||||||
*/
|
|
|
@ -1,63 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cmath>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Константные ссылки нужны прежде всего, чтобы передавать большие объекты в функции, внутри которых они не должны меняться
|
|
||||||
|
|
||||||
Рассмотрим структуру Book, чей размер более 100 байт
|
|
||||||
|
|
||||||
|
|
||||||
1) При передаче такой структуры в функцию по значению, как это происходит в функции printBookV,
|
|
||||||
вся структура будет копироваться внутрь функции и это очень медленно. Так делать не стоит.
|
|
||||||
|
|
||||||
|
|
||||||
2) При передаче такой структуры в функцию по обычной ссылке, как это происходит в функции printBookR, структура не копируется
|
|
||||||
На самом деле, под капотом внутрь функции копируется адрес структуры.
|
|
||||||
Адрес намного меньше самой структуры, поэтому это копирование работает намного быстрее.
|
|
||||||
|
|
||||||
Но возникает проблема с тем, что структура внутри такой функции может поменяться.
|
|
||||||
В реальной ситуации, если функций много и они большие, уследить за тем меняется ли аргументы внутри функций становится проблематично.
|
|
||||||
|
|
||||||
|
|
||||||
3) При передаче такой структуры в функцию по константной ссылке, как это происходит в функции printBookCR, структура не копируется.
|
|
||||||
Плюс к этому мы можем быть уверены, что внутри функции наша структура не поменяется и это сильно упрощает понимание программы.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
struct Book
|
|
||||||
{
|
|
||||||
char title[100];
|
|
||||||
int pages;
|
|
||||||
float price;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
void printBookV(Book b)
|
|
||||||
{
|
|
||||||
cout << b.title << ", pages = " << b.pages << ", price = " << b.price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void printBookR(Book& b)
|
|
||||||
{
|
|
||||||
cout << b.title << ", pages = " << b.pages << ", price = " << b.price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void printBookCR(const Book& b)
|
|
||||||
{
|
|
||||||
cout << b.title << ", pages = " << b.pages << ", price = " << b.price << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Book b = {"War and Peace", 1200, 900};
|
|
||||||
|
|
||||||
printBookV(b);
|
|
||||||
printBookR(b);
|
|
||||||
printBookCR(b);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
|
@ -1,50 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Ссылки можно и возвращать из функции
|
|
||||||
Например, функция get возвращает ссылку на глобальную переменную x
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int x = 10;
|
|
||||||
|
|
||||||
|
|
||||||
int& get()
|
|
||||||
{
|
|
||||||
return x;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << x << endl;
|
|
||||||
cout << get() << endl;
|
|
||||||
|
|
||||||
get() += 1;
|
|
||||||
cout << x << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
С указателями аналогичный код выглядел бы так:
|
|
||||||
|
|
||||||
|
|
||||||
int x = 10;
|
|
||||||
|
|
||||||
int* get()
|
|
||||||
{
|
|
||||||
return &x;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << x << endl;
|
|
||||||
cout << *get() << endl;
|
|
||||||
|
|
||||||
*get() += 1;
|
|
||||||
cout << x << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,51 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Ссылки можно и возвращать из функции
|
|
||||||
|
|
||||||
Но при этом нужно следить за тем, чтобы функция не вернула ссылку на локальную переменную, как это происходит в данном примере.
|
|
||||||
После завершения функции, переменная x удалится, так как она была определена внутри функции.
|
|
||||||
|
|
||||||
В результате, внутри функции main мы попробуем доступиться к области памяти, в которой раньше лежала переменная x.
|
|
||||||
Это приведёт к ошибке
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int& get()
|
|
||||||
{
|
|
||||||
int x = 10;
|
|
||||||
return x;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << get() << endl;
|
|
||||||
|
|
||||||
get() += 1;
|
|
||||||
cout << get() << endl;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Аналогичная ошибка может произойти и при работе с обычными указателями:
|
|
||||||
|
|
||||||
int* get()
|
|
||||||
{
|
|
||||||
int x = 10;
|
|
||||||
return &x;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << *get() << endl;
|
|
||||||
|
|
||||||
*get() += 1;
|
|
||||||
cout << *get() << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,39 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Ссылки можно и возвращать из функции
|
|
||||||
Например, функция increase принимает ссылку, увеличивет то, на что указывает эта ссылка на 1
|
|
||||||
и возвращает эту ссылку
|
|
||||||
|
|
||||||
При этом никакого копирование самой переменной a в функцию и из функции не происходит
|
|
||||||
*/
|
|
||||||
|
|
||||||
int& increase(int& r)
|
|
||||||
{
|
|
||||||
r += 1;
|
|
||||||
return r;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
|
|
||||||
cout << "1) a = " << a << endl;
|
|
||||||
|
|
||||||
increase(a);
|
|
||||||
cout << "2) a = " << a << endl;
|
|
||||||
|
|
||||||
increase(a) += 7;
|
|
||||||
cout << "3) a = " << a << endl;
|
|
||||||
|
|
||||||
increase(increase(increase(a)));
|
|
||||||
cout << "4) a = " << a << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Что напечатает данная программа?
|
|
||||||
*/
|
|
|
@ -1,17 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите функцию multiplyBy2, которая принимает число по ссылке и увеличивает его в 2 раза
|
|
||||||
Вызовите эту функцию из функции main
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,16 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
void multiplyBy2(int& a)
|
|
||||||
{
|
|
||||||
a *= 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int x = 10;
|
|
||||||
multiplyBy2(x);
|
|
||||||
cout << x << endl;
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,22 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите функцию sumAndSave, которая должна принимать 3 аргумента
|
|
||||||
Первые два аргумента по значению
|
|
||||||
Третий аргумент по ссылке
|
|
||||||
|
|
||||||
Функция должна складывать первые 2 аргумента и сохранять результат по третей ссылке
|
|
||||||
|
|
||||||
Вызовите эту функцию из функции main
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,36 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите функцию sumAndSave, которая должна принимать 3 аргумента
|
|
||||||
Первые два аргумента по значению
|
|
||||||
Третий аргумент по ссылке
|
|
||||||
|
|
||||||
Функция должна складывать первые 2 аргумента и сохранять результат по третей ссылке
|
|
||||||
|
|
||||||
Вызовите эту функцию из функции main
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
void sumAndSave(int a, int b, int& c)
|
|
||||||
{
|
|
||||||
c = a + b;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int x = 10, y = 20;
|
|
||||||
int z;
|
|
||||||
|
|
||||||
sumAndSave(x, y, z);
|
|
||||||
cout << z << endl;
|
|
||||||
|
|
||||||
|
|
||||||
sumAndSave(70, 80, z);
|
|
||||||
cout << z << endl;
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите функцию
|
|
||||||
|
|
||||||
void calculateLetters(char str[], int& numLetters)
|
|
||||||
|
|
||||||
Которая будет принимать на вход строку и считать количество строчных букв в этой строке
|
|
||||||
Строчные буквы - это символы от 'a' и до 'z'
|
|
||||||
|
|
||||||
Например, вызов calculateLetters("ab54AB,gd1:e", x) должен сохранить число 5 в переменную x
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
|
|
||||||
int x;
|
|
||||||
calculateLetters("ab54AB,gd1:e", x);
|
|
||||||
cout << x << endl;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,23 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void calculateLetters(char str[], int& numLetters)
|
|
||||||
{
|
|
||||||
numLetters = 0;
|
|
||||||
for (int i = 0; str[i] != '\0'; ++i)
|
|
||||||
{
|
|
||||||
if (str[i] >= 'a' && str[i] <= 'z')
|
|
||||||
numLetters += 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int x;
|
|
||||||
calculateLetters("ab54AB,gd1:e", x);
|
|
||||||
cout << x << endl;
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,61 +0,0 @@
|
||||||
#include <stdio.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Это программа на языке C и компилировать её надо так:
|
|
||||||
gcc 00cfunctions.c
|
|
||||||
|
|
||||||
|
|
||||||
Известно, что в языке C нельзя создать две функции с одинаковым названием
|
|
||||||
Но часто требуется написать функции, которые будут делать похожие вещи, но для разных типов данных.
|
|
||||||
Простейший пример -- математические функции для разных численных типов данных
|
|
||||||
|
|
||||||
В языке C эта проблема решается так, что функциям даются немного различающиеся имена
|
|
||||||
|
|
||||||
|
|
||||||
В данном примере мы создали функции для вычисления абсолютного значения для типов int и double
|
|
||||||
Всё работает хорошо, пока мы соблюдаем типы данных и функции
|
|
||||||
|
|
||||||
Но стоит ошибиться и произойдёт сложно выявляемая ошибка
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int abs(int a)
|
|
||||||
{
|
|
||||||
if (a < 0)
|
|
||||||
return -a;
|
|
||||||
else
|
|
||||||
return a;
|
|
||||||
}
|
|
||||||
|
|
||||||
double fabs(double a)
|
|
||||||
{
|
|
||||||
if (a < 0)
|
|
||||||
return -a;
|
|
||||||
else
|
|
||||||
return a;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printf("%i\n", abs(-5));
|
|
||||||
printf("%lf\n", fabs(-5.9));
|
|
||||||
|
|
||||||
|
|
||||||
double x = abs(-5.9);
|
|
||||||
printf("%lf\n", x);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) В данном примере переменная x равна ровно 5. Почему так происходит?
|
|
||||||
|
|
||||||
2) Что будет, если всё-таки назвать 2 функции одинаковым именем и скомпилировать программу с помощью gcc?
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,66 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Это программа на языке C++ и компилировать её надо так:
|
|
||||||
g++ 01cppfunctions.c
|
|
||||||
|
|
||||||
|
|
||||||
В отличии от языка C в языке C++ есть возможность создать 2 и больше разных функции с одним и тем же названием,
|
|
||||||
но с разным количеством и/или типами аргументов.
|
|
||||||
|
|
||||||
Компилятор сам догадается, какую функцию следует вызвать в зависимости от типа аргумента.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int abs(int a)
|
|
||||||
{
|
|
||||||
if (a < 0)
|
|
||||||
return -a;
|
|
||||||
else
|
|
||||||
return a;
|
|
||||||
}
|
|
||||||
|
|
||||||
double abs(double a)
|
|
||||||
{
|
|
||||||
if (a < 0)
|
|
||||||
return -a;
|
|
||||||
else
|
|
||||||
return a;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << abs(-5) << endl;
|
|
||||||
cout << abs(-5.9) << endl;
|
|
||||||
|
|
||||||
|
|
||||||
double x = abs(-5.9);
|
|
||||||
cout << x << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Протестируйте, что компилятор действительно вызывает нужные функции
|
|
||||||
Для этого просто сделайте так, чтобы функция, которая принимает int печатала на экран слово int,
|
|
||||||
а функция, которая принимает double, печатала бы на экран слово double
|
|
||||||
|
|
||||||
|
|
||||||
2) Что если на вход функции abs передать тип float?
|
|
||||||
Например, вот так:
|
|
||||||
abs(1.5f)
|
|
||||||
|
|
||||||
Какая из функций вызовется?
|
|
||||||
|
|
||||||
|
|
||||||
3) Напишите ещё одну перегрузку функции abs для типа float
|
|
||||||
Протестируйте её в функции main
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,30 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите несколько перегруженных функций под названием max
|
|
||||||
|
|
||||||
1) max, который вычисляет максимум от двух чисел типа int
|
|
||||||
2) max, который вычисляет максимум от двух чисел типа double
|
|
||||||
3) max, который вычисляет максимум от трёх чисел типа int
|
|
||||||
4) max, который вычисляет максимум от трёх чисел типа double
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
int max(int a, int b)
|
|
||||||
{
|
|
||||||
if (a > b)
|
|
||||||
return a;
|
|
||||||
else
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << max(4.2, 2.8) << endl; // Выводит число 4 -- неправильно
|
|
||||||
}
|
|
|
@ -1,53 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
int max(int a, int b)
|
|
||||||
{
|
|
||||||
if (a > b)
|
|
||||||
return a;
|
|
||||||
else
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
double max(double a, double b)
|
|
||||||
{
|
|
||||||
if (a > b)
|
|
||||||
return a;
|
|
||||||
else
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
int max(int a, int b, int c)
|
|
||||||
{
|
|
||||||
int result = a;
|
|
||||||
if (b > result)
|
|
||||||
result = b;
|
|
||||||
if (c > result)
|
|
||||||
result = c;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
double max(double a, double b, double c)
|
|
||||||
{
|
|
||||||
double result = a;
|
|
||||||
if (b > result)
|
|
||||||
result = b;
|
|
||||||
if (c > result)
|
|
||||||
result = c;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << max(4.2, 2.8) << endl;
|
|
||||||
|
|
||||||
cout << max(1, 2) << endl;
|
|
||||||
|
|
||||||
cout << max(4, 2, 5) << endl;
|
|
||||||
|
|
||||||
cout << max(1.2, 2.1, 0.5) << endl;
|
|
||||||
}
|
|
|
@ -1,42 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите несколько перегруженных функций под названием printType
|
|
||||||
|
|
||||||
Эти функции должны печатать тип переменной, которая поступает на вход
|
|
||||||
|
|
||||||
|
|
||||||
printType(15) должен напечатать int
|
|
||||||
printType(1.5) должен напечатать double
|
|
||||||
printType(1.5f); должен напечатать float
|
|
||||||
printType("Hello"); должен напечатать char[]
|
|
||||||
|
|
||||||
book b = {"War and Peace", 900, 1200};
|
|
||||||
printType(b); должен напечатать book
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
struct book
|
|
||||||
{
|
|
||||||
char title[50];
|
|
||||||
float price;
|
|
||||||
int pages;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printType(15);
|
|
||||||
printType(1.5);
|
|
||||||
printType(1.5f);
|
|
||||||
printType("Hello");
|
|
||||||
|
|
||||||
book b = {"War and Peace", 900, 1200};
|
|
||||||
printType(b);
|
|
||||||
}
|
|
|
@ -1,66 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Напишите несколько перегруженных функций под названием printType
|
|
||||||
|
|
||||||
Эти функции должны печатать тип переменной, которая поступает на вход
|
|
||||||
|
|
||||||
|
|
||||||
printType(15) должен напечатать int
|
|
||||||
printType(1.5) должен напечатать double
|
|
||||||
printType(1.5f); должен напечатать float
|
|
||||||
printType("Hello"); должен напечатать char[]
|
|
||||||
|
|
||||||
book b = {"War and Peace", 900, 1200};
|
|
||||||
printType(b); должен напечатать book
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
struct book
|
|
||||||
{
|
|
||||||
char title[50];
|
|
||||||
float price;
|
|
||||||
int pages;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
void printType(int a)
|
|
||||||
{
|
|
||||||
cout << "int" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printType(double a)
|
|
||||||
{
|
|
||||||
cout << "double" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printType(float a)
|
|
||||||
{
|
|
||||||
cout << "float" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printType(const char a[])
|
|
||||||
{
|
|
||||||
cout << "char[]" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void printType(const book& a)
|
|
||||||
{
|
|
||||||
cout << "book" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printType(15);
|
|
||||||
printType(1.5);
|
|
||||||
printType(1.5f);
|
|
||||||
printType("Hello");
|
|
||||||
|
|
||||||
book b = {"War and Peace", 900, 1200};
|
|
||||||
printType(b);
|
|
||||||
}
|
|
|
@ -1,17 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cmath>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
В отличии от языка C в языке C++ стандартные математические функции уже перегружены и могут
|
|
||||||
работать с разными типами данных
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
cout << std::abs(-4) << endl;
|
|
||||||
cout << std::abs(-4.2) << endl;
|
|
||||||
cout << std::abs(-4.2f) << endl;
|
|
||||||
}
|
|
|
@ -1,67 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Функции можно перегружать и по указателю и ссылке
|
|
||||||
|
|
||||||
Но в случае с перегрузкой по ссылке могут возникнуть ситуации при которых невозможно выбрать правильный
|
|
||||||
|
|
||||||
Например, при вызове
|
|
||||||
|
|
||||||
int a = 10;
|
|
||||||
func(a);
|
|
||||||
|
|
||||||
Можно выбрать функцию void func(int x) или void func(int& x)
|
|
||||||
Определить более правильную функцию в этом случае невозможно, это приведёт к ошибке
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
void func(int x)
|
|
||||||
{
|
|
||||||
cout << "int x" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void func(int* x)
|
|
||||||
{
|
|
||||||
cout << "int* x" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void func(int& x)
|
|
||||||
{
|
|
||||||
cout << "int& x" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
int* p = &a;
|
|
||||||
int& r = a;
|
|
||||||
|
|
||||||
func(a);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Определите какая функция вызовется при следующих вызовах функции func или произойдёт ошибка
|
|
||||||
|
|
||||||
1) func(a)
|
|
||||||
2) func(p)
|
|
||||||
3) func(&a)
|
|
||||||
4) func(20)
|
|
||||||
5) func(r)
|
|
||||||
6) func(&r)
|
|
||||||
|
|
||||||
|
|
||||||
2) Если добавить перегрузку, принимающую по константной ссылке, то что изменится
|
|
||||||
|
|
||||||
void func(const int& x)
|
|
||||||
{
|
|
||||||
cout << "const int& x" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,30 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
struct Cat {};
|
|
||||||
struct Dog {};
|
|
||||||
struct Cow {};
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void say(Cat a)
|
|
||||||
{
|
|
||||||
cout << "Meow" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void say(Dog a)
|
|
||||||
{
|
|
||||||
cout << "Woof" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
void say(Cow a)
|
|
||||||
{
|
|
||||||
cout << "Mooo" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Cow x;
|
|
||||||
say(x);
|
|
||||||
}
|
|
|
@ -1,48 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Предположим, что мы захотели создать структуру, который будет хранить время (для простоты, только минуты и секунды)
|
|
||||||
|
|
||||||
Нам может понадобиться функция, которая будет добавлять ко времени, некоторое количество секунд
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time add(Time t, int x)
|
|
||||||
{
|
|
||||||
Time result = t;
|
|
||||||
result.seconds += x;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {20, 10};
|
|
||||||
Time b = add(a, 90);
|
|
||||||
|
|
||||||
cout << b.minutes << " " << b.seconds << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) Напишите функцию, которая будет складывать не время и число, а два времени
|
|
||||||
|
|
||||||
Time add(Time ta, Time tb)
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,44 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time add(Time t, int x)
|
|
||||||
{
|
|
||||||
Time result = t;
|
|
||||||
result.seconds += x;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
Time add(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {20, 10};
|
|
||||||
Time b = add(a, 90);
|
|
||||||
Time c = add(a, b);
|
|
||||||
|
|
||||||
cout << b.minutes << " " << b.seconds << endl;
|
|
||||||
cout << c.minutes << " " << c.seconds << endl;
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,63 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Использовать функции может быть не так удобно как операторы.
|
|
||||||
Возможно было бы удобней для добавления времени использовать не функцию add, а оператор +
|
|
||||||
|
|
||||||
Можно перегрузить оператор функцией, для этого нужно назвать функцию так: operator@
|
|
||||||
где за место @ нужно подставить оператор, который вы хотите перегрузить
|
|
||||||
|
|
||||||
Например, функция Time operator+(Time t, int x) перегружает оператор + для типов Time и int соответственно (обязательно в таком порядке)
|
|
||||||
Теперь, когда компилятор встретит в коде сложение с таким операндами он вызовет эту функцию
|
|
||||||
|
|
||||||
В этом примере a + 90 при компиляции преобразуется в вызов функции operator+(a, 90)
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time operator+(Time t, int x)
|
|
||||||
{
|
|
||||||
Time result = t;
|
|
||||||
result.seconds += x;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {20, 10};
|
|
||||||
Time b = a + 90;
|
|
||||||
|
|
||||||
cout << b.minutes << " " << b.seconds << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) Что если операторы сложения поменяются местами
|
|
||||||
Time b = 90 + a;
|
|
||||||
Сработает ли в этом случае наша функция operator+ и, если нет, что нужно добавить, чтобы такое сложение сработало?
|
|
||||||
|
|
||||||
|
|
||||||
2) Напишите перегруженный оператор, который будет складывать не время и число, а два времени
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,50 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time operator+(Time t, int x)
|
|
||||||
{
|
|
||||||
Time result = t;
|
|
||||||
result.seconds += x;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Time operator+(int x, Time t)
|
|
||||||
{
|
|
||||||
return t + x;
|
|
||||||
}
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {20, 10};
|
|
||||||
Time b = a + 90;
|
|
||||||
Time c = 90 + a;
|
|
||||||
Time d = a + b;
|
|
||||||
|
|
||||||
cout << b.minutes << " " << b.seconds << endl;
|
|
||||||
cout << c.minutes << " " << c.seconds << endl;
|
|
||||||
cout << d.minutes << " " << d.seconds << endl;
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,71 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Помимо перегрузки операторов, принимающих 2 аргумента (бинарных)
|
|
||||||
можно перегружать и унарные операторы - принимающие один аргумент
|
|
||||||
|
|
||||||
При этом, так как operator+ это функция, то работает перегрузка функций
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
cout << "binary operator +" << endl;
|
|
||||||
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Time operator+(Time t)
|
|
||||||
{
|
|
||||||
cout << "unary operator +" << endl;
|
|
||||||
|
|
||||||
return t;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {20, 10};
|
|
||||||
Time b = {40, 30};
|
|
||||||
|
|
||||||
Time c = a + b;
|
|
||||||
Time d = +a;
|
|
||||||
|
|
||||||
cout << c.minutes << " " << c.seconds << endl;
|
|
||||||
cout << d.minutes << " " << d.seconds << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) Что если операторы сложения поменяются местами
|
|
||||||
Time b = 90 + a;
|
|
||||||
Сработает ли в этом случае наша функция operator+ и, если нет, что нужно добавить, чтобы такое сложение сработало?
|
|
||||||
|
|
||||||
|
|
||||||
2) Напишите перегруженный оператор, который будет складывать не время и число, а два времени
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,38 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
В прошлом семестре, для хранения результатов логических операций, мы использовали целочисленные типы (например int).
|
|
||||||
|
|
||||||
В языке C++ есть встроенный тип bool, который может принимать 2 значения (true и false).
|
|
||||||
Для хранения значения логических переменных желательно использовать этот тип
|
|
||||||
|
|
||||||
|
|
||||||
При печати на экран с помощью std::cout переменных типа bool печатается либо 0 либо 1
|
|
||||||
Чтобы на экран печаталось false или true нужно в std::cout передать специальный объект std::boolalpha
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
bool isEven(int a)
|
|
||||||
{
|
|
||||||
return a % 2 == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
bool a = isEven(10);
|
|
||||||
bool b = isEven(15);
|
|
||||||
bool c = a || b;
|
|
||||||
|
|
||||||
|
|
||||||
if (c)
|
|
||||||
cout << "Yes" << endl;
|
|
||||||
else
|
|
||||||
cout << "No" << endl;
|
|
||||||
|
|
||||||
cout << c << endl;
|
|
||||||
cout << std::boolalpha << c << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
|
@ -1,68 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Помимо арифметических операторов можно перегружать и операторы сравнения (и многие другие операторы)
|
|
||||||
Желательно, чтобы операторы сравнения возвращали bool
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator>(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
bool result = false;
|
|
||||||
|
|
||||||
if (ta.minutes > tb.minutes)
|
|
||||||
result = true;
|
|
||||||
else if (ta.minutes == tb.minutes && ta.seconds > tb.seconds)
|
|
||||||
result = true;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {10, 20};
|
|
||||||
Time b = {10, 40};
|
|
||||||
Time c = {0, 20};
|
|
||||||
|
|
||||||
cout << std::boolalpha;
|
|
||||||
cout << (a > b) << endl;
|
|
||||||
cout << (b > a) << endl;
|
|
||||||
cout << (a + c > b) << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) Заметьте, что при выводе на экран сравнение было взято в скобки
|
|
||||||
cout << (a > b) << endl;
|
|
||||||
|
|
||||||
Что будет, если эти скобки не писать и почему
|
|
||||||
cout << a > b << endl;
|
|
||||||
|
|
||||||
|
|
||||||
2) Напишите перегруженные операторы < >= <= == != для сравнения объектов структур типа Time друг с другом
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,110 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Помимо арифметических операторов можно перегружать и операторы сравнения (и многие другие операторы)
|
|
||||||
Желательно, чтобы операторы сравнения возвращали bool
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator>(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
bool result = false;
|
|
||||||
|
|
||||||
if (ta.minutes > tb.minutes)
|
|
||||||
result = true;
|
|
||||||
else if (ta.minutes == tb.minutes && ta.seconds > tb.seconds)
|
|
||||||
result = true;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator==(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
bool result = false;
|
|
||||||
if (ta.minutes == tb.minutes && ta.seconds == tb.seconds)
|
|
||||||
result = true;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool operator!=(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
return !(ta == tb);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator>=(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
return ta > tb || ta == tb;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator<(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
return !(ta >= tb);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
bool operator<=(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
return !(ta > tb);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {10, 20};
|
|
||||||
Time b = {10, 40};
|
|
||||||
Time c = {0, 20};
|
|
||||||
|
|
||||||
cout << std::boolalpha;
|
|
||||||
cout << (a == b) << endl;
|
|
||||||
cout << (a != b) << endl;
|
|
||||||
|
|
||||||
cout << (a < b) << endl;
|
|
||||||
cout << (a <= b) << endl;
|
|
||||||
cout << (a > b) << endl;
|
|
||||||
cout << (a >= b) << endl;
|
|
||||||
cout << (a + c >= b) << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
1) Заметьте, что при выводе на экран сравнение было взято в скобки
|
|
||||||
cout << (a > b) << endl;
|
|
||||||
|
|
||||||
Что будет, если эти скобки не писать и почему
|
|
||||||
cout << a > b << endl;
|
|
||||||
|
|
||||||
Ошибка происходит из-за того, что приоритет операции << выше, чем у операций сравнения
|
|
||||||
В результате сначала проводится
|
|
||||||
cout << a
|
|
||||||
затем получившийся объект сравнивается с b. Это и приводит к ошибке.
|
|
||||||
*/
|
|
|
@ -1,49 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
Перегрузка оператора << для вывода на экран
|
|
||||||
|
|
||||||
Напомним, что объект под названием cout имеет тип ostream (сокращение от output stream - выходной поток)
|
|
||||||
и хранится в библиотеке iostream в пространстве имён std
|
|
||||||
|
|
||||||
То есть где-то внутри библиотеки iostream объявлена глобальная переменная по имени cout типа ostream
|
|
||||||
ostream cout;
|
|
||||||
|
|
||||||
|
|
||||||
Мы можем перегрузить оператор << с первым аргументом типа std::ostream, а вторым аргументом - нашим типом,
|
|
||||||
чтобы удобно выводить на экран объекты нашего типа.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
void operator<<(std::ostream& out, Time t)
|
|
||||||
{
|
|
||||||
out << t.minutes << ":" << t.seconds;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {10, 20};
|
|
||||||
cout << a;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
cout << a; работает, но
|
|
||||||
cout << a << endl; выдаёт ошибку в данной программе.
|
|
||||||
|
|
||||||
Из-за чего это происходит и как исправить эту ошибку?
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,63 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
std::ostream& operator<<(std::ostream& out, Time t)
|
|
||||||
{
|
|
||||||
out << t.minutes << ":" << t.seconds;
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {10, 20};
|
|
||||||
Time b = {15, 50};
|
|
||||||
|
|
||||||
cout << a << endl << b << endl;
|
|
||||||
cout << a + b << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
cout << a; работает, но
|
|
||||||
cout << a << endl; выдаёт ошибку в данной программе.
|
|
||||||
|
|
||||||
Из-за чего это происходит и как исправить эту ошибку?
|
|
||||||
|
|
||||||
|
|
||||||
Решение:
|
|
||||||
|
|
||||||
Ошибка происходила из-за того, что оператор << ничего не возвращал.
|
|
||||||
|
|
||||||
В строке cout << a << endl;
|
|
||||||
результат cout << a был void и к нему нельзя применить оператор << ещё раз.
|
|
||||||
|
|
||||||
|
|
||||||
Результат cout << a должен быть тоже быть равен cout
|
|
||||||
Но, поскольку глобальный объект cout копировать мы не можем, у нас остаётся единственный выход:
|
|
||||||
принимать и возвращать объект cout по ссылке.
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,52 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
struct Complex
|
|
||||||
{
|
|
||||||
float re, im;
|
|
||||||
};
|
|
||||||
|
|
||||||
Complex operator+(Complex first, Complex second)
|
|
||||||
{
|
|
||||||
Complex result = {first.re + second.re, first.im + second.im};
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Complex z1 = {3, 7};
|
|
||||||
Complex z2 = {2, -4};
|
|
||||||
|
|
||||||
Complex z = z1 + z2;
|
|
||||||
cout << z.re << " + " << z.im << "i" << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задачи:
|
|
||||||
|
|
||||||
1) Перегрузите следующие операторы:
|
|
||||||
- Вычитание
|
|
||||||
- Умножение
|
|
||||||
- Деление
|
|
||||||
- Унарный минус
|
|
||||||
- Унарный плюс
|
|
||||||
- Сравнение ==
|
|
||||||
- Сопряжение - это операция, которая меняет знак мнимой части комплексного числа
|
|
||||||
Для сопряжения используйте оператор унарная звёздочка *
|
|
||||||
|
|
||||||
2) Перегрузите оператор вывода <<
|
|
||||||
|
|
||||||
3) Напишите функцию exp(z)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
cout << z1 - z2 << endl;
|
|
||||||
cout << z1 * z2 << endl;
|
|
||||||
cout << z1 / z2 << endl;
|
|
||||||
cout << -z1 << endl;
|
|
||||||
cout << *z1 << endl; // (Комплексно-сопряжённое)
|
|
||||||
|
|
||||||
z = exp(z1 + z2)/(z1 * z2);
|
|
||||||
cout << z << endl;
|
|
||||||
*/
|
|
|
@ -1,52 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <iomanip>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
В библиотеки iomanip содержатся специальные функции, для работы с потоками ostream
|
|
||||||
|
|
||||||
setw - установить минимальный размер в символах для печати следующего объекта
|
|
||||||
setfill - если размер печати меньше минимального, то замостить оставшееся соответствующим символом
|
|
||||||
|
|
||||||
setprecision - установить точность (для вещественных чисел)
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
struct Time
|
|
||||||
{
|
|
||||||
int minutes;
|
|
||||||
int seconds;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
Time operator+(Time ta, Time tb)
|
|
||||||
{
|
|
||||||
Time result = ta;
|
|
||||||
result.seconds += 60 * tb.minutes + tb.seconds;
|
|
||||||
|
|
||||||
result.minutes += (result.seconds / 60);
|
|
||||||
result.seconds %= 60;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
std::ostream& operator<<(std::ostream& out, Time t)
|
|
||||||
{
|
|
||||||
out << std::setfill('0') << std::setw(2) << t.minutes << ":" <<
|
|
||||||
std::setfill('0') << std::setw(2) << t.seconds;
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
Time a = {1, 5};
|
|
||||||
Time b = {4, 20};
|
|
||||||
|
|
||||||
cout << a << endl << b << endl;
|
|
||||||
cout << a + b << endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
|
@ -1,52 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cstdlib>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
В отличии от языка C, язык C++ не делает неявное преобразование типов указателей.
|
|
||||||
|
|
||||||
Рассмотрим, например, код:
|
|
||||||
|
|
||||||
int a = 10;
|
|
||||||
char* p = &a;
|
|
||||||
|
|
||||||
В языке C такой код сработает, несмотря на то, что в строке char* p = &a; слева стоит указатель типа char*
|
|
||||||
а справа объект типа int*. Будет произведено неявное преобразование типов указателей.
|
|
||||||
|
|
||||||
В языке C++ такой код приведёт к ошибке, так как C++ не преобразует указатели неявно.
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Рассмотрим, например, код:
|
|
||||||
|
|
||||||
int* q = malloc(10 * sizeof(int));
|
|
||||||
|
|
||||||
В языке C такой код сработает, несмотря на то, что слева стоит указатель типа int*
|
|
||||||
а справа объект типа void* (malloc возвращает указатель типа void*).
|
|
||||||
Будет произведено неявное преобразование типов указателей.
|
|
||||||
|
|
||||||
В языке C++ такой код приведёт к ошибке, так как C++ не преобразует указатели неявно.
|
|
||||||
*/
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
char* p = &a;
|
|
||||||
|
|
||||||
|
|
||||||
int* q = malloc(10 * sizeof(int));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
|
|
||||||
Задача:
|
|
||||||
|
|
||||||
Исправьте ошибки компиляции, явно приведя указатель к правильным типам.
|
|
||||||
|
|
||||||
*/
|
|
|
@ -1,13 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cstdlib>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
char* p = (char*)&a;
|
|
||||||
|
|
||||||
|
|
||||||
int* q = (int*)malloc(10 * sizeof(int));
|
|
||||||
}
|
|
|
@ -1,17 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
#include <cstdlib>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
В языке C++ желательно использовать более безопасное приведение типов static_cast
|
|
||||||
*/
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
int a = 10;
|
|
||||||
char* p = static_cast<char*>(&a);
|
|
||||||
|
|
||||||
|
|
||||||
int* q = static_cast<int*>(malloc(10 * sizeof(int)));
|
|
||||||
}
|
|
|
@ -1,50 +0,0 @@
|
||||||
#include <cstdio>
|
|
||||||
|
|
||||||
/*
|
|
||||||
Новое специальное нулевое значение для указателя: nullptr
|
|
||||||
В языке C для этой цели использовался NULL, который был просто числом 0
|
|
||||||
|
|
||||||
Если определить NULL так:
|
|
||||||
|
|
||||||
#define NULL (void*)0
|
|
||||||
|
|
||||||
То, в отличии от языка C, в языке C++ простая строка вида:
|
|
||||||
|
|
||||||
int* p = NULL;
|
|
||||||
|
|
||||||
не сработает, так как слева стоит int* а справа void*
|
|
||||||
|
|
||||||
|
|
||||||
Если определить NULL так:
|
|
||||||
|
|
||||||
#define NULL 0
|
|
||||||
|
|
||||||
то в C++ могут возникнуть проблемы с перегрузкой, как это показано ниже.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
void print(int value)
|
|
||||||
{
|
|
||||||
printf("Int: %d\n", value);
|
|
||||||
}
|
|
||||||
|
|
||||||
void print(void* pointer)
|
|
||||||
{
|
|
||||||
printf("Pointer: %p\n", pointer);
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
void* p1 = NULL;
|
|
||||||
void* p2 = nullptr;
|
|
||||||
|
|
||||||
// Всё ОК (компилятор может выбрать функцию):
|
|
||||||
print(p1);
|
|
||||||
print(p2);
|
|
||||||
|
|
||||||
// Тут неверно (компилятор не может выбрать перегруженную функцию, произойдёт ошибка):
|
|
||||||
print(NULL);
|
|
||||||
|
|
||||||
// Тут всё OK:
|
|
||||||
print(nullptr);
|
|
||||||
}
|
|
|
@ -1,42 +0,0 @@
|
||||||
#include <iostream>
|
|
||||||
using std::cout, std::endl;
|
|
||||||
|
|
||||||
/*
|
|
||||||
В отличии от языка C, в C++ можно задавать значения по умолчанию
|
|
||||||
для аргументов функций
|
|
||||||
|
|
||||||
Функцию printSquare можно вызвать с одним, двумя или тремя
|
|
||||||
параметрами. Аргументы width и height будут заданы аргументами по умолчанию.
|
|
||||||
Если передаваемых аргументов будет меньше трёх.
|
|
||||||
*/
|
|
||||||
|
|
||||||
void printSquare(char c, int width = 10, int height = 5)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < width; i++)
|
|
||||||
{
|
|
||||||
for (int j = 0; j < height; j++)
|
|
||||||
{
|
|
||||||
cout << c;
|
|
||||||
}
|
|
||||||
cout << endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int main()
|
|
||||||
{
|
|
||||||
printSquare('+', 6, 4);
|
|
||||||
printSquare('#', 15);
|
|
||||||
printSquare('O');
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
Задание:
|
|
||||||
|
|
||||||
1) Написать функцию:
|
|
||||||
void print(char str[], bool isCapitalized = false)
|
|
||||||
Которая будет просто печатать строку str, если isCapitalized = false,
|
|
||||||
а если isCapitalized = true, то будет печатать всю строку в верхнем регистре
|
|
||||||
*/
|
|
|
@ -1,160 +0,0 @@
|
||||||
\documentclass{article}
|
|
||||||
\usepackage[utf8x]{inputenc}
|
|
||||||
\usepackage{ucs}
|
|
||||||
\usepackage{amsmath}
|
|
||||||
\usepackage{amsfonts}
|
|
||||||
\usepackage{marvosym}
|
|
||||||
\usepackage{wasysym}
|
|
||||||
\usepackage{upgreek}
|
|
||||||
\usepackage[english,russian]{babel}
|
|
||||||
\usepackage{graphicx}
|
|
||||||
\usepackage{float}
|
|
||||||
\usepackage{textcomp}
|
|
||||||
\usepackage{hyperref}
|
|
||||||
\usepackage{geometry}
|
|
||||||
\geometry{left=2cm}
|
|
||||||
\geometry{right=1.5cm}
|
|
||||||
\geometry{top=1cm}
|
|
||||||
\geometry{bottom=2cm}
|
|
||||||
\usepackage{tikz}
|
|
||||||
\usepackage{ccaption}
|
|
||||||
\usepackage{multicol}
|
|
||||||
|
|
||||||
\usepackage{listings}
|
|
||||||
%\setlength{\columnsep}{1.5cm}
|
|
||||||
%\setlength{\columnseprule}{0.2pt}
|
|
||||||
|
|
||||||
\usepackage{colortbl,graphicx,tikz}
|
|
||||||
\definecolor{X}{rgb}{.5,.5,.5}
|
|
||||||
|
|
||||||
\title{ДЗ. Работа с изображениями в формате \texttt{.ppm}}
|
|
||||||
\date{}
|
|
||||||
\begin{document}
|
|
||||||
\pagenumbering{gobble}
|
|
||||||
|
|
||||||
\lstset{
|
|
||||||
language=C++, % choose the language of the code
|
|
||||||
basicstyle=\linespread{1.1}\ttfamily,
|
|
||||||
columns=fixed,
|
|
||||||
fontadjust=true,
|
|
||||||
basewidth=0.5em,
|
|
||||||
keywordstyle=\color{blue}\bfseries,
|
|
||||||
commentstyle=\color{gray},
|
|
||||||
stringstyle=\ttfamily\color{orange!50!black},
|
|
||||||
showstringspaces=false,
|
|
||||||
%numbers=false, % where to put the line-numbers
|
|
||||||
numbersep=5pt,
|
|
||||||
numberstyle=\tiny\color{black},
|
|
||||||
numberfirstline=true,
|
|
||||||
stepnumber=1, % the step between two line-numbers.
|
|
||||||
numbersep=10pt, % how far the line-numbers are from the code
|
|
||||||
backgroundcolor=\color{white}, % choose the background color. You must add \usepackage{color}
|
|
||||||
showstringspaces=false, % underline spaces within strings
|
|
||||||
captionpos=b, % sets the caption-position to bottom
|
|
||||||
breaklines=true, % sets automatic line breaking
|
|
||||||
breakatwhitespace=true, % sets if automatic breaks should only happen at whitespace
|
|
||||||
xleftmargin=.2in,
|
|
||||||
extendedchars=\true,
|
|
||||||
keepspaces = true,
|
|
||||||
}
|
|
||||||
\lstset{literate=%
|
|
||||||
*{0}{{{\color{red!20!violet}0}}}1
|
|
||||||
{1}{{{\color{red!20!violet}1}}}1
|
|
||||||
{2}{{{\color{red!20!violet}2}}}1
|
|
||||||
{3}{{{\color{red!20!violet}3}}}1
|
|
||||||
{4}{{{\color{red!20!violet}4}}}1
|
|
||||||
{5}{{{\color{red!20!violet}5}}}1
|
|
||||||
{6}{{{\color{red!20!violet}6}}}1
|
|
||||||
{7}{{{\color{red!20!violet}7}}}1
|
|
||||||
{8}{{{\color{red!20!violet}8}}}1
|
|
||||||
{9}{{{\color{red!20!violet}9}}}1
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
\title{Семинар \#1: Ссылки и перегрузка операторов. Домашнее задание.\vspace{-5ex}}\date{}\maketitle
|
|
||||||
\subsection*{Пространство имён:}
|
|
||||||
\begin{itemize}
|
|
||||||
\item Создайте пространство имён по имени \texttt{myspace}. В этом пространстве имён создайте функцию \\
|
|
||||||
\texttt{void print\_n\_times(char str[], int n = 10)}, которая будет печатать строку \texttt{str} \texttt{n} раз. Для печати используйте \texttt{std::cout} из библиотеки \texttt{iostream}. Вызовите эту функцию из \texttt{main}.
|
|
||||||
\end{itemize}
|
|
||||||
|
|
||||||
\subsection*{Ссылки:}
|
|
||||||
\begin{itemize}
|
|
||||||
\item Напишите функцию \texttt{cube}, которая будет принимать одно число типа \texttt{int} и возводить его в куб. Используйте ссылки. Вызовите эту функцию из функции \texttt{main}.
|
|
||||||
\item Напишите функцию \texttt{void count\_letters(char str[], int\& n\_letters, int\& n\_digits, int\& n\_other)}, которая будет принимать на вход строку \texttt{str} и подсчитывать число букв и цифр в этой строке. Количество букв нужно записать в переменную \texttt{n\_letters}, количество цифр -- в переменную \texttt{n\_digits}, а количество остальных символов -- в переменную \texttt{n\_other}. Вызвать эту функцию из функции \texttt{main}.
|
|
||||||
\end{itemize}
|
|
||||||
|
|
||||||
\subsection*{Перегрузка операций:}
|
|
||||||
В файлах \texttt{code/complex.h} и \texttt{code/complex.cpp} лежит реализация комплексного числа с перегруженными операторами. Используйте его в качестве примера для решения задач этого раздела:
|
|
||||||
\begin{itemize}
|
|
||||||
\item Создайте структуру \texttt{Vector3f} - вектор в трёхмерном пространстве с полями \texttt{x, y, z} типа \texttt{float} в качестве координат. Перегрузите следующие операторы для работы с вектором. Для передачи вектора в функции используте ссылки и, там где возможно, модификатор \texttt{const}.
|
|
||||||
\begin{itemize}
|
|
||||||
\item Сложение векторов (\texttt{+})
|
|
||||||
\item Вычитание (\texttt{-})
|
|
||||||
\item Умножение вектора на число типа \texttt{float} (число \texttt{*} вектор и вектор \texttt{*} число)
|
|
||||||
\item Деление вектора на число типа \texttt{float} (вектор \texttt{/} число)
|
|
||||||
\item Скалярное произведение (\texttt{*})
|
|
||||||
\item Унарный \texttt{-}
|
|
||||||
\item Унарный \texttt{+}
|
|
||||||
\item Проверка на равенство \texttt{==} (должна возвращать тип \texttt{bool})
|
|
||||||
\item Проверка на неравенство \texttt{!=} (должна возвращать тип \texttt{bool})
|
|
||||||
\item Операторы \texttt{+=} и \texttt{-=} (вектор \texttt{+=} вектор)
|
|
||||||
\item Операторы \texttt{*=} и \texttt{/=} (вектор \texttt{*=} число)
|
|
||||||
\item Оператор вывода \texttt{ostream >{}>} вектор. Выводите вектор в виде \texttt{(x, y, z)}.
|
|
||||||
\item Оператор ввода \texttt{istream <{}<} вектор
|
|
||||||
\item Функция \texttt{float squared\_norm(const Vector3f\& a)}, которая вычисляет квадрат нормы вектора.
|
|
||||||
\item Функция \texttt{float norm(const Vector3f\& a)}, которая вычисляет норму вектора.
|
|
||||||
\item Функция \texttt{void normalize(Vector3f\& a)}, которая нормализует вектор \texttt{a}.
|
|
||||||
\end{itemize}
|
|
||||||
\item Поместите весь ваш код в отдельный файл \texttt{vector3f.h} и подключите к файлу \texttt{main.cpp}.
|
|
||||||
\item Протестируйте ваши функции:
|
|
||||||
\begin{lstlisting}
|
|
||||||
#include <iostream>
|
|
||||||
#include "vector3f.h"
|
|
||||||
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
|
|
||||||
int main() {
|
|
||||||
Vector3f a = {1.0, 2.0, -2.0};
|
|
||||||
Vector3f b = {4.0, -1.0, 3.0};
|
|
||||||
cout << "a = " << a << endl << "b = " << b << endl;
|
|
||||||
cout << "a + b = " << a + b << endl;
|
|
||||||
cout << "-a = " << -a << endl;
|
|
||||||
cout << "Scalar product of a and b = " << a * b << endl;
|
|
||||||
a /= 5;
|
|
||||||
cout << "a after a /= 5;" << a << endl
|
|
||||||
normalize(b);
|
|
||||||
cout << "Normalized b:" << b << endl
|
|
||||||
a += b;
|
|
||||||
cout << "a after a+= b;" << a << endl;
|
|
||||||
}
|
|
||||||
\end{lstlisting}
|
|
||||||
|
|
||||||
\end{itemize}
|
|
||||||
\subsection*{Задача об убегающей точке}
|
|
||||||
\begin{itemize}
|
|
||||||
\item Предположим, что у нас есть комплексная функция $f(z) = z^2$. Выберем некоторое комплексное число $z_0$ и будем проводить следующие итерации:
|
|
||||||
\begin{equation}
|
|
||||||
\label{fractalseq}
|
|
||||||
z_1 = f(z_0)\quad z_2 = f(z_1)\quad ...\quad z_{k+1} = f(z_k)\quad ...
|
|
||||||
\end{equation}
|
|
||||||
В зависимости от выбора точки $z_0$ эта последовательность либо разойдётся, либо останется в некоторой ограниченной области. Будем называть точку $z_0$ убегающей, если $z_k \rightarrow \infty$ при $k \rightarrow \infty$. Найдите область неубегания для функции $z^2$, т.е. множество всех начальных значений $z_0$, при которых последовательность (\ref{fractalseq}) остаётся ограниченной (это можно сделать в уме). \\
|
|
||||||
|
|
||||||
\item \textbf{Julia:} Для функции $f(z) = z^2$ эта область тривиальна, но всё становится сложней для функции вида $f(z) = z^2 + c$, где $c$ -- некоторое комплексное число. Численно найдите область неубегания для функций такого вида. Для этого создайте изображение размера 800x800, покрывающую область \texttt{[-2:2]x[-2:2]} на комплексной плоскости. Для каждой точки этой плоскости проведите $N \approx 20$ итераций и, в зависимости от результата, окрасьте пиксель в соответствующий цвет (цвет можно подобрать самим, он должен быть пропорционален значению $z_N$ - меняться от яркого если $z_N$ мало и до черного если $z_N$ большое). Используйте класс Complex и перегруженные операторы. Пример работы с изображениями в формате \texttt{ppm} можно посмотреть в файле \texttt{complex\_image.cpp}. Программа должна создавать файл \texttt{julia.ppm}.
|
|
||||||
|
|
||||||
\begin{center}
|
|
||||||
\includegraphics[scale=0.7]{../images/complexplane.png}
|
|
||||||
\end{center}
|
|
||||||
|
|
||||||
\item Нарисуте изображение для $c = -0.4 + 0.6i$;\quad $c = -0.70 - 0.38i$;\quad $c = -0.80 + 0.16i$\quad и\quad $c = 0.280 + 0.011i$.
|
|
||||||
\item Добавьте параметры командной строки: 2 вещественных числа, соответствующие комплексному числу $c$, и целое число итераций $N$.
|
|
||||||
\item \textbf{Mandelbrot:} Зафиксируем теперь $z_0 = 0$ и будем менять $c$. Численно найдите все параметры $c$, для которых точка $z_0$ не является убегающей. Для этого создайте изображение размера 800x800, покрывающую область \texttt{[-2:2]x[-2:2]} возможных значений $c$ на комплексной плоскости. Программа должна создавать файл \texttt{mandelbrot.ppm}.
|
|
||||||
|
|
||||||
\item \textbf{Анимация:} Программа \texttt{complex\_movie.cpp} создаёт множество изображений и сохраняет их в папку \texttt{animation} (если у вас нет такой папки -- создайте её). Эти изображения представляют собой отдельные кадры будущей анимации. Чтобы их объединить в одно видео можно использовать программу ffmpeg (Нужно скачать тут: \href{https://www.ffmpeg.org/}{www.ffmpeg.org} и изменить переменную среды \texttt{PATH} в настройках Windows или Linux). После этого можно будет объединить все изображения в одно видео такой командой:
|
|
||||||
\begin{verbatim}
|
|
||||||
ffmpeg -r 60 -i animation/complex_%03d.ppm complex_movie.mp4
|
|
||||||
\end{verbatim}
|
|
||||||
Создайте анимацию из изображений множеств Julia при $c$ линейно меняющемся от $(-1.5 - 0.5i)$ до $i$.
|
|
||||||
\end{itemize}
|
|
||||||
\end{document}
|
|
Binary file not shown.
Before Width: | Height: | Size: 51 KiB |
|
@ -1,490 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
|
||||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
|
||||||
|
|
||||||
<svg
|
|
||||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
|
||||||
xmlns:cc="http://creativecommons.org/ns#"
|
|
||||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
|
||||||
xmlns:svg="http://www.w3.org/2000/svg"
|
|
||||||
xmlns="http://www.w3.org/2000/svg"
|
|
||||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
|
||||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
|
||||||
width="210mm"
|
|
||||||
height="297mm"
|
|
||||||
viewBox="0 0 210 297"
|
|
||||||
version="1.1"
|
|
||||||
id="svg8"
|
|
||||||
inkscape:version="0.92.4 (5da689c313, 2019-01-14)"
|
|
||||||
sodipodi:docname="complexplane.svg"
|
|
||||||
inkscape:export-filename="C:\Users\vova\workspace\latex\cs_mipt_faki\term2\seminar01_overload\images\complexplane.png"
|
|
||||||
inkscape:export-xdpi="300"
|
|
||||||
inkscape:export-ydpi="300">
|
|
||||||
<defs
|
|
||||||
id="defs2">
|
|
||||||
<marker
|
|
||||||
inkscape:isstock="true"
|
|
||||||
style="overflow:visible"
|
|
||||||
id="marker4404"
|
|
||||||
refX="0.0"
|
|
||||||
refY="0.0"
|
|
||||||
orient="auto"
|
|
||||||
inkscape:stockid="TriangleOutM">
|
|
||||||
<path
|
|
||||||
transform="scale(0.4)"
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
id="path4402" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="TriangleOutM"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="marker3702"
|
|
||||||
style="overflow:visible"
|
|
||||||
inkscape:isstock="true"
|
|
||||||
inkscape:collect="always">
|
|
||||||
<path
|
|
||||||
id="path3700"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.4)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:isstock="true"
|
|
||||||
style="overflow:visible"
|
|
||||||
id="marker1848"
|
|
||||||
refX="0.0"
|
|
||||||
refY="0.0"
|
|
||||||
orient="auto"
|
|
||||||
inkscape:stockid="TriangleOutM"
|
|
||||||
inkscape:collect="always">
|
|
||||||
<path
|
|
||||||
transform="scale(0.4)"
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
id="path1846" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="TriangleOutL"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="marker1755"
|
|
||||||
style="overflow:visible"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
id="path1753"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.8)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="TriangleOutM"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="TriangleOutM"
|
|
||||||
style="overflow:visible"
|
|
||||||
inkscape:isstock="true"
|
|
||||||
inkscape:collect="always">
|
|
||||||
<path
|
|
||||||
id="path962"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.4)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="Arrow2Mend"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="Arrow2Mend"
|
|
||||||
style="overflow:visible;"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
id="path844"
|
|
||||||
style="fill-rule:evenodd;stroke-width:0.625;stroke-linejoin:round;stroke:#000000;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
|
||||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="Arrow1Send"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="Arrow1Send"
|
|
||||||
style="overflow:visible;"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
id="path832"
|
|
||||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.2) rotate(180) translate(6,0)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="Arrow1Mend"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="Arrow1Mend"
|
|
||||||
style="overflow:visible;"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
id="path826"
|
|
||||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="TriangleOutL"
|
|
||||||
orient="auto"
|
|
||||||
refY="0.0"
|
|
||||||
refX="0.0"
|
|
||||||
id="TriangleOutL"
|
|
||||||
style="overflow:visible"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
id="path959"
|
|
||||||
d="M 5.77,0.0 L -2.88,5.0 L -2.88,-5.0 L 5.77,0.0 z "
|
|
||||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;stroke-opacity:1;fill:#000000;fill-opacity:1"
|
|
||||||
transform="scale(0.8)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:stockid="Arrow2Mend"
|
|
||||||
orient="auto"
|
|
||||||
refY="0"
|
|
||||||
refX="0"
|
|
||||||
id="Arrow2Mend-1"
|
|
||||||
style="overflow:visible"
|
|
||||||
inkscape:isstock="true">
|
|
||||||
<path
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
id="path844-7"
|
|
||||||
style="fill:#000000;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.625;stroke-linejoin:round;stroke-opacity:1"
|
|
||||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
|
||||||
transform="scale(-0.6)" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:isstock="true"
|
|
||||||
style="overflow:visible"
|
|
||||||
id="marker1848-1"
|
|
||||||
refX="0"
|
|
||||||
refY="0"
|
|
||||||
orient="auto"
|
|
||||||
inkscape:stockid="TriangleOutM">
|
|
||||||
<path
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
transform="scale(0.4)"
|
|
||||||
style="fill:#000000;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.00000003pt;stroke-opacity:1"
|
|
||||||
d="M 5.77,0 -2.88,5 V -5 Z"
|
|
||||||
id="path1846-2" />
|
|
||||||
</marker>
|
|
||||||
<marker
|
|
||||||
inkscape:isstock="true"
|
|
||||||
style="overflow:visible"
|
|
||||||
id="marker1848-1-0"
|
|
||||||
refX="0"
|
|
||||||
refY="0"
|
|
||||||
orient="auto"
|
|
||||||
inkscape:stockid="TriangleOutM">
|
|
||||||
<path
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
transform="scale(0.4)"
|
|
||||||
style="fill:#000000;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.00000003pt;stroke-opacity:1"
|
|
||||||
d="M 5.77,0 -2.88,5 V -5 Z"
|
|
||||||
id="path1846-2-9" />
|
|
||||||
</marker>
|
|
||||||
</defs>
|
|
||||||
<sodipodi:namedview
|
|
||||||
id="base"
|
|
||||||
pagecolor="#ffffff"
|
|
||||||
bordercolor="#666666"
|
|
||||||
borderopacity="1.0"
|
|
||||||
inkscape:pageopacity="0.0"
|
|
||||||
inkscape:pageshadow="2"
|
|
||||||
inkscape:zoom="0.98994949"
|
|
||||||
inkscape:cx="353.12978"
|
|
||||||
inkscape:cy="607.47601"
|
|
||||||
inkscape:document-units="mm"
|
|
||||||
inkscape:current-layer="layer1"
|
|
||||||
showgrid="false"
|
|
||||||
inkscape:window-width="2048"
|
|
||||||
inkscape:window-height="1089"
|
|
||||||
inkscape:window-x="-8"
|
|
||||||
inkscape:window-y="-8"
|
|
||||||
inkscape:window-maximized="1" />
|
|
||||||
<metadata
|
|
||||||
id="metadata5">
|
|
||||||
<rdf:RDF>
|
|
||||||
<cc:Work
|
|
||||||
rdf:about="">
|
|
||||||
<dc:format>image/svg+xml</dc:format>
|
|
||||||
<dc:type
|
|
||||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
|
||||||
<dc:title></dc:title>
|
|
||||||
</cc:Work>
|
|
||||||
</rdf:RDF>
|
|
||||||
</metadata>
|
|
||||||
<g
|
|
||||||
inkscape:label="Layer 1"
|
|
||||||
inkscape:groupmode="layer"
|
|
||||||
id="layer1">
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.5;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;stroke-miterlimit:4;stroke-dasharray:none;marker-end:url(#Arrow2Mend)"
|
|
||||||
d="M 40.892237,140.11279 H 184.68324"
|
|
||||||
id="path815"
|
|
||||||
inkscape:connector-curvature="0" />
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.44465432;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;marker-end:url(#Arrow2Mend-1)"
|
|
||||||
d="M 111.09637,191.55795 V 77.837989"
|
|
||||||
id="path815-0"
|
|
||||||
inkscape:connector-curvature="0" />
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.3160204;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628"
|
|
||||||
cx="111.0882"
|
|
||||||
cy="140.01112"
|
|
||||||
r="0.76016355" />
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8"
|
|
||||||
cx="148.20093"
|
|
||||||
cy="118.06308"
|
|
||||||
r="1.2027128" />
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#8c8c8c;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-7"
|
|
||||||
cx="122.00854"
|
|
||||||
cy="111.38131"
|
|
||||||
r="1.2027128" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="149.13637"
|
|
||||||
y="123.00754"
|
|
||||||
id="text1662"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1660"
|
|
||||||
x="149.13637"
|
|
||||||
y="123.00754"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:64.99999762%;font-family:Consolas;-inkscape-font-specification:Consolas;baseline-shift:sub"
|
|
||||||
id="tspan1664">0</tspan></tspan></text>
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="117.36532"
|
|
||||||
y="107.94124"
|
|
||||||
id="text1662-1"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1660-7"
|
|
||||||
x="117.36532"
|
|
||||||
y="107.94124"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:64.99999762%;baseline-shift:sub"
|
|
||||||
id="tspan1691">0</tspan><tspan
|
|
||||||
style="font-size:64.99999762%;baseline-shift:super"
|
|
||||||
id="tspan1693">2</tspan></tspan></text>
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.26499999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;marker-end:url(#TriangleOutM)"
|
|
||||||
d="m 148.06731,118.19668 c -11.62623,3.07361 -18.17432,2.67269 -24.58879,-4.67721"
|
|
||||||
id="path1695"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.28318167px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-end:url(#marker1848)"
|
|
||||||
d="m 122.80545,110.44543 7.46851,-10.603435"
|
|
||||||
id="path1823"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-1"
|
|
||||||
cx="131.8873"
|
|
||||||
cy="97.715988"
|
|
||||||
r="1.2027128" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="132.06721"
|
|
||||||
y="94.73333"
|
|
||||||
id="text1662-2"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1660-4"
|
|
||||||
x="132.06721"
|
|
||||||
y="94.73333"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:64.99999762%;baseline-shift:sub"
|
|
||||||
id="tspan1931">1</tspan></tspan></text>
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="127.48359"
|
|
||||||
y="106.24847"
|
|
||||||
id="text1935"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1933"
|
|
||||||
x="127.48359"
|
|
||||||
y="106.24847"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:3.17499995px;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">c</tspan></text>
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-1-4"
|
|
||||||
cx="83.3881"
|
|
||||||
cy="93.474258"
|
|
||||||
r="1.2027128" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="83.92263"
|
|
||||||
y="90.667931"
|
|
||||||
id="text1963"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1961"
|
|
||||||
x="83.92263"
|
|
||||||
y="90.667931"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:64.99999762%;baseline-shift:sub"
|
|
||||||
id="tspan1965">2</tspan></tspan></text>
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#8c8c8c;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-7-4"
|
|
||||||
cx="73.736542"
|
|
||||||
cy="106.99813"
|
|
||||||
r="1.2027128" />
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.28318167px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-end:url(#marker1848-1)"
|
|
||||||
d="m 74.533458,106.06225 7.46851,-10.603432"
|
|
||||||
id="path1823-5"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="66.792633"
|
|
||||||
y="105.14875"
|
|
||||||
id="text1662-1-8"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1660-7-8"
|
|
||||||
x="66.792633"
|
|
||||||
y="105.14875"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:65%;baseline-shift:sub"
|
|
||||||
id="tspan3362">1</tspan><tspan
|
|
||||||
style="font-size:3.21027756px;baseline-shift:super;stroke-width:0.26458332"
|
|
||||||
id="tspan1693-5">2</tspan></tspan></text>
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-1-4-5"
|
|
||||||
cx="104.43866"
|
|
||||||
cy="160.09435"
|
|
||||||
r="1.2027128" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="104.97319"
|
|
||||||
y="157.28801"
|
|
||||||
id="text1963-6"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1961-6"
|
|
||||||
x="104.97319"
|
|
||||||
y="157.28801"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:65%;baseline-shift:sub"
|
|
||||||
id="tspan3474">3</tspan></tspan></text>
|
|
||||||
<circle
|
|
||||||
style="opacity:1;fill:#8c8c8c;fill-opacity:1;stroke:#000000;stroke-width:0.5;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1"
|
|
||||||
id="path1628-8-7-4-8"
|
|
||||||
cx="94.787102"
|
|
||||||
cy="173.61821"
|
|
||||||
r="1.2027128" />
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.28318167px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-end:url(#marker1848-1-0)"
|
|
||||||
d="m 95.584015,172.68232 7.468515,-10.60343"
|
|
||||||
id="path1823-5-8"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="87.843193"
|
|
||||||
y="171.76883"
|
|
||||||
id="text1662-1-8-4"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan1660-7-8-2"
|
|
||||||
x="87.843193"
|
|
||||||
y="171.76883"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">z<tspan
|
|
||||||
style="font-size:65%;baseline-shift:sub"
|
|
||||||
id="tspan3472">2</tspan><tspan
|
|
||||||
style="font-size:3.21027756px;baseline-shift:super;stroke-width:0.26458332"
|
|
||||||
id="tspan1693-5-9">2</tspan></tspan></text>
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
|
||||||
d="m 161.77381,138.43899 v 3.96875"
|
|
||||||
id="path3476"
|
|
||||||
inkscape:connector-curvature="0" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="162.52975"
|
|
||||||
y="144.77008"
|
|
||||||
id="text3480"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan3478"
|
|
||||||
x="162.52975"
|
|
||||||
y="144.77008"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">1</tspan></text>
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
|
||||||
d="m 62.552971,138.29726 v 3.96875"
|
|
||||||
id="path3476-9"
|
|
||||||
inkscape:connector-curvature="0" />
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="62.552963"
|
|
||||||
y="144.62834"
|
|
||||||
id="text3480-1"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan3478-1"
|
|
||||||
x="62.552963"
|
|
||||||
y="144.62834"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">-1</tspan></text>
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="180.29465"
|
|
||||||
y="145.43155"
|
|
||||||
id="text3516"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan3514"
|
|
||||||
x="180.29465"
|
|
||||||
y="145.43155"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">Re</tspan></text>
|
|
||||||
<text
|
|
||||||
xml:space="preserve"
|
|
||||||
style="font-style:normal;font-weight:normal;font-size:4.93888855px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.26458332"
|
|
||||||
x="114.01411"
|
|
||||||
y="78.19413"
|
|
||||||
id="text3516-5"><tspan
|
|
||||||
sodipodi:role="line"
|
|
||||||
id="tspan3514-5"
|
|
||||||
x="114.01411"
|
|
||||||
y="78.19413"
|
|
||||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Consolas;-inkscape-font-specification:Consolas;stroke-width:0.26458332">Im</tspan></text>
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000002;stroke-width:0.2;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;marker-end:url(#marker3702);stroke-dashoffset:0"
|
|
||||||
d="M 131.0957,96.547854 C 114.25772,93.206983 83.588544,102.82868 76.03818,106.50365"
|
|
||||||
id="path3692"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
<path
|
|
||||||
style="fill:none;stroke:#000000;stroke-width:0.26499999;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;marker-end:url(#marker4404)"
|
|
||||||
d="M 82.185379,92.605629 C 39.819072,91.505729 40.154686,168.69649 91.71736,174.07274"
|
|
||||||
id="path4394"
|
|
||||||
inkscape:connector-curvature="0"
|
|
||||||
sodipodi:nodetypes="cc" />
|
|
||||||
</g>
|
|
||||||
</svg>
|
|
Before Width: | Height: | Size: 21 KiB |
Some files were not shown because too many files have changed in this diff Show more
Reference in a new issue