Loading...

Във форума е въведено ограничение, което позволява на потребителите единствено да разглеждат публикуваните въпроси.

Filipbg avatar Filipbg 26 Точки

Task 1 Pipes

#include <iostream>
#include <cmath>
#include <array>
using namespace std;

int main()
{
    int numberOfPipes = 0;
    int lifetimes = 0;
    array<int, 100> checkup = {0};
    array<int, 100> installation = {0};
    cin >> numberOfPipes;
    if(numberOfPipes > 0 && numberOfPipes <= 500)
    {
        for(int i = 0; i < numberOfPipes; ++i)
        {
            cin >> checkup[i];
        }
        for(int n = 0; n < numberOfPipes; ++n)
        {
            cin >> installation[n];
        }
        if(installation.size() > 0 && installation.size() <= 500)
        {
            for(int i = 0; i < numberOfPipes; ++i)
            {
                if(checkup[i] < installation[i])
                {
                    lifetimes = abs(checkup[i] - installation[i]);
                }
                else
                {
                    lifetimes = installation[i];
                }
                cout << lifetimes << " ";
            }
        }
    }
    return 0;
}

От задачата разбирам че годините се намират като се извадят всички checkup от installation. Или бъркам логиката за изчисляването на годините?

Тагове:
0
C++ Fundamentals
MartinBG avatar MartinBG 4803 Точки
Best Answer

По условие се търси след колко години тръбата трябва да бъде заменена (0 - трябва да се смени веднага, 1 - след 1 година и т.н.). Годините се получават като се извади здравината от текущото (new) замерване от предходното (old) замерване - така получаваме стъпката на износване и с нея делим текущата здравина (new):

years = new  / (old new)

 

В решението ти има много ненужни проверки (проверяваш неща, които по условие са ти гарантирани) и това може би те обърква допълнително.

Следните валидации са излишни:

if(numberOfPipes > 0 && numberOfPipes <= 500)

if(installation.size() > 0 && installation.size() <= 500)

if(checkup[i] < installation[i])

 

0
Filipbg avatar Filipbg 26 Точки

Благодаря за отговора. Реших я но Judge даде 60/100 и 4 Runtime Errors. Нямам идея къде греша :/ 
EDIT: Промених масивите с големина 500 и мина. Явно това са имали в предвид в условието.

#include <iostream>
#include <cmath>
#include <array>
using namespace std;

int main()
{
int numberOfPipes = 0;
int lifetimes[] = {0};
array<int, 100> checkup = {0};
array<int, 100> installation = {0};
cin >> numberOfPipes;
for(int i = 0; i < numberOfPipes; ++i)
{
    cin >> checkup[i];
}
for(int n = 0; n < numberOfPipes; ++n)
{
    cin >> installation[n];
}
for(int i = 0; i < numberOfPipes; ++i)
{
lifetimes[i] = 1.0 * installation[i] / (checkup[i] - installation[i]);
cout << abs(lifetimes[i]) << " ";
}
return 0;
}

 

0
27/09/2019 18:17:22
MartinBG avatar MartinBG 4803 Точки

В случая по-удачно е да използваш vector вместо array, тъй като размерът му може да се променя динамично (т.е. по време на изпълнение на програмата), а не е фиксиран:

 

#include <iostream>
#include <vector>
using namespace std;

int main()
{
  int numberOfPipes;
  vector<int> checkup;
  vector<int> installation;
  cin >> numberOfPipes;
  int pipeStrength;
  for(int i = 0; i < numberOfPipes; ++i)
  {
    cin >> pipeStrength;
    checkup.push_back(pipeStrength);
  }
  for(int n = 0; n < numberOfPipes; ++n)
  {
    cin >> pipeStrength;
    installation.push_back(pipeStrength);
  }
  for(int i = 0; i < numberOfPipes; ++i)
  {
    int yearsLeft = installation[i] / (checkup[i] - installation[i]);
    cout << yearsLeft << " ";
  }
  return 0;
}

 

0
zzerro avatar zzerro 16 Точки

Здравейте!

Аз нещо не разбрах.. Следното работи:

void readArr(vector<int> &inArr)
{
    for(size_t i = 0; i < inArr.size(); ++i)
        cin >> inArr[i];
}

Обаче ето така не става:

void readArr(vector<int> &inArr)
{
    for(int i : inArr)
        cin >> inArr[i];
}

Защо?

0
MartinBG avatar MartinBG 4803 Точки

@zzerro

// inArr = { 0, 0, 0, 0, 0 }
for(size_t i = 0; i < inArr.size(); ++i) {
    // i ще е 0, 1, 2, 3, 4
    inArr[i] = 42; 
}
// inArr = { 42, 42, 42, 42, 42 }


// inArr = { 0, 0, 0, 0, 0 }
for(int i : inArr) { // обхождат се стойностите на inArr
    // i ще е 0, 0, 0, 0, 0 (стойностите на елементите в inArr)
    inArr[i] = 42;
}
// inArr = { 42, 0, 0, 0, 0 }

 

0
30/09/2019 03:51:10
zzerro avatar zzerro 16 Точки

Благодаря, @ MartinBG !

 

А, това изглежда ли ти безопасно?

    for(auto &dataOnly : inArr)
        cin >> dataOnly;

 

0
kolioi avatar kolioi 641 Точки

@zzerro

Зависи как точно си дефинирал inArr. Ако това е масив с 10 елемента

int inArr[10];

тогава трябва да прочетеш точно 10 числа от тип int. Ако inArr е вектор дефиниран така

vector<int> inArr;

тогава размера му е 0 и няма да прочетеш нищо. Затова трябва да зададеш размер на вектора и този код ще върви без проблем

int vSize = 5;
vector<int> inArr(vSize);
for(auto &dataOnly : inArr)
    cin >> dataOnly;

или така

vector<int> inArr;
inArr.resize(5);

Значи range-based for loop за който питаш обхожда всички елементи на масива (или друг контейнер, напр. map, set, list и т.н.) и обикновено се използва при печатане например, а при въвеждане трябва или да използваш обикновен for loop, или да зададеш предварително размера на контейнера за да знаеш колко числа да прочетеш от входа.

1
spasimira25 avatar spasimira25 25 Точки

zzero, Възприемаш малко погрешно for range цикъла. Тук "i" е стойност, а не номер на итерация. Не можеш да го използваш за да се добереш директно до индекса на вектора или масива. За да го направиш трябва да вкараш брояч да речем. Т.е тук "i" може да е float или double или char , bооlean или дори string. Просто C++ вижда следното: имам вектор с размер 0-10 и стойности от някакъв тип: "изведи ми тези стойности една по една". За да не се бъркаш не си кръщавай във фор-рейндж цикъл променливата i (iterator). Ако искаш ще ти дам решение на - "3.Problem 3 – Remove" със местене, запис, триене във фор-рейндж. Но не знам дали няма да те объркам повече. Затова ето нещо по лесно. Сравенение между рейндж и нормален цикъл:

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main (){
  
    vector<string> vec = {"asdf", "qwert", "zxcv"} ;

   for (string n : vec){
    cout<<n<<endl;
   }
   for (int i=0 ;i<3;i++){
    cout<<vec[i]<<" ";
   }
}

 

0
30/09/2019 11:54:15
spasimira25 avatar spasimira25 25 Точки

Етро ти горното, допълнено  с въвеждане вътре във фор-рейндж. И последващия му печат.

#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main (){
    int remove_number;


    vector<string> vec = {"asdf", "qwert", "zxcv"} ;

   for (string n : vec){
    cout<<n<<endl;
   }
   for (int i=0 ;i<3;i++){
    cout<<vec[i]<<" ";
   }

cout<<"Molia vuvedete 3 dumi"<<endl;
   int i = 0;
    for (string n : vec){
    cin>>n;
    vec[i]=n;
     i++;
    }
    for (string n : vec){
        cout<<n<<endl;
    }
}

 

0
zzerro avatar zzerro 16 Точки

Да, @ kolioi, искам да ползвам вектор като динамичен масив с размер, определен по време на изпълнението. Благодаря за добрия отговор!

0
zzerro avatar zzerro 16 Точки

Не ме объркваш, @ spasimira25. Но ако ще трябва да правим това:

cout<<"Molia vuvedete 3 dumi"<<endl;
   int i = 0;
    for (string n : vec){
    cin>>n;
    vec[i]=n;
     i++;
    }

То май е по-добре да си ползваме обикновен.

0
spasimira25 avatar spasimira25 25 Точки

Да, за въвеждане и според мен е по-добре обикновен цикъл. Винаги можеш да си извлечеш размера на вектора ( и капацитета ). Но пък рейндж цикъла ми изглежда удобен за вадене на инфо. Сигурно има и други удобства де.

0
02/10/2019 17:19:24
daisy_c avatar daisy_c 3 Точки

@ zzerro

Мисля, че е защото, когато използваш втория тип итериране

for(int i : inArr)

цикъла обикаля по такъв начин елементите, че не можеш да позлваш индексите им и не можеш да намериш кой е

inArr[i]

елемента. А при първия начин обикаляш, като пазиш в промеливата i самия индекс, до който си стигнал.

Също така, когато използваш този for

for(size_t i = 0; i < inArr.size(); ++i)

ти можеш да запълваш масива като викаш всяко място по индекса, до който си стигнал. Но при другия for, работиш директно със самия елемент и няма как да го запълниш със cin, ами получаваш каквото вече има във масива. Например ако пробваш това:

for(int var : inArr){
        cin >> var;
        inArr.push_back(var);
    }

 

for(int i : inArr){
        cout << i;
    }

ако си си занулил вектора в началото и въведеш 1 2 3, програмата, ще ти даде 000123, защото за всеки съществуващ елемент във вектора (трите нули, които вече имаме), добавяш към вектора нова стойност въведена от конзолата (1 2 3) към вече съществуващите, стойности.

0
galin_kostadinov avatar galin_kostadinov 166 Точки

Привет!

void readArr(vector<int> &inArr)
{
    for(int i : inArr)
        cin >> inArr[i];
}

Тук итерираш, вървеш последователно по елементите на вектрора.

Да речем, че вече си напълни вектора с елементи {17, 5, 7, 13}.

Тръгвайки итератора ти дава първия елемент, който в случая е равен на i = 17.

Тук ти му казвай, запиши ми на инекс i = 17 -> inArr[17] нещо прочетено от конзолния вход.

Ако има индек 17 в твоя масив ще стане, но това не е желания резултат в случая.

 

void readArr(vector<int> &inArr)
{
    for(size_t i = 0; i < inArr.size(); ++i)
        cin >> inArr[i];
}

Тук вървиш последователно по индексите, първо i = 0, после i=1... и записваш на тази позиция нещо прочетено от конзолата.

Поздрави!

 

 

 

0
Можем ли да използваме бисквитки?
Ние използваме бисквитки и подобни технологии, за да предоставим нашите услуги. Можете да се съгласите с всички или част от тях.
Назад
Функционални
Използваме бисквитки и подобни технологии, за да предоставим нашите услуги. Използваме „сесийни“ бисквитки, за да Ви идентифицираме временно. Те се пазят само по време на активната употреба на услугите ни. След излизане от приложението, затваряне на браузъра или мобилното устройство, данните се трият. Използваме бисквитки, за да предоставим опцията „Запомни Ме“, която Ви позволява да използвате нашите услуги без да предоставяте потребителско име и парола. Допълнително е възможно да използваме бисквитки за да съхраняваме различни малки настройки, като избор на езика, позиции на менюта и персонализирано съдържание. Използваме бисквитки и за измерване на маркетинговите ни усилия.
Рекламни
Използваме бисквитки, за да измерваме маркетинг ефективността ни, броене на посещения, както и за проследяването дали дадено електронно писмо е било отворено.