Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Клуб программистов > Свободное общение
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 11.01.2012, 09:05   #191
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от ITTI Посмотреть сообщение
в векторе дни недели. пользователь вводит название дня и значение, если такой день есть - значение сохраняется. это понятно, но к примеру, в векторе "Monday", а если введено "monday" или "Mon" - значение не игнорируется. что делать с этими синонимами?
Ничего не понял..
Кэп, нужно что бы "Monday", "monday", "Mon" были синонимами? Или наоборот, что бы левые игнорировались?
_Bers вне форума Ответить с цитированием
Старый 12.01.2012, 18:56   #192
ITTI
Пользователь
 
Регистрация: 19.12.2011
Сообщений: 65
По умолчанию

Цитата:
Сообщение от _Bers Посмотреть сообщение
Ничего не понял..
Кэп, нужно что бы "Monday", "monday", "Mon" были синонимами? Или наоборот, что бы левые игнорировались?
в векторе, вроде бы, "Monday" и т.п., но если вводишь "monday" - это не ошибка, но если "Funday", то, понятно, ошибка.
ITTI вне форума Ответить с цитированием
Старый 12.01.2012, 19:10   #193
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от ITTI Посмотреть сообщение
в векторе, вроде бы, "Monday" и т.п., но если вводишь "monday" - это не ошибка, но если "Funday", то, понятно, ошибка.
Вектор векторов.

"Monday", "mon", "понедельник" <--- это первый вектор, содержащий список синонимов
"вторник", "втор" <--- это второй вектор, содержащий список синонимов

И тд.

Все эти вектора вместе - это вектор векторов.

Идентификация дня: пробежаться по всему вектору векторов, искать до тех пор пока не обнаружится нужный день, либо пока не будут перебором исследованы все элементы.


Можно оптимизировать процесс идентификации данных: глянуть в сторону ассоциативного массива map

Элемент асоциативного массива, это ключ (день недели, например "понедельник"), и значение - индекс элемента в векторе, который хранит истинное значение дня недели (например: 0 - это понедельник)

Тогда можно запихать в ассоциативный массив сколько угодно разных ключей, ссылающихся на один и тот же индекс в векторе, а следовательно разные ключи, ссылающиеся на одно и тоже значение - суть синонимы.

В такой системе поиск элемента по ключу среди любых 100500 возможных синонимов выполняется очень быстро. (А вот вставки-удаления медленно. Если не нужно на лету постоянно добавлять-удалять новые элементы-синонимы, то этот способ - оптимальное решение по скорости. Если нужно постоянно добавлять-удалять, нужно придумать что нибудь поинтереснее)

Иллюстрация-концепт:

Мап заполняется по следующей схеме: ключ, значение.
Где ключ - строка, обозначающая синоним.
Значение - индекс в векторе, значение которого - истинная строка, синонимом которой является ключ мапа, на него ссылающийся

Примерное содержимое мапа:
"понедельник" , 0
"пон", 0
"втор" ,1
"вторник", 1

Примерное содержимое вектора:
"Понедельник"
"Вторник"

Теперь мы ищем в мапе по ключу:

Вернуть значение элемента с заданным ключем (допустим "пон"). Тогда значение вернётся - 0.
По индексу 0 в векторе находится значение "Понедельник". Значит "пон" синоним "Понедельник".
Если же в мапе отсутствует элемент с заданным ключом - значит заданный ключ не_валидный.

Поиск данных через ключи-синонимы даже в очень большом массиве происходит практически мгновенно.

Здесь примитивное описание std::map на русском:
http://adorning.ru/2010/01/18/s-urok...ivnyiy-massiv/

Здесь - добротное описание на английском
http://www.cplusplus.com/reference/stl/map/

Последний раз редактировалось _Bers; 12.01.2012 в 19:20.
_Bers вне форума Ответить с цитированием
Старый 13.01.2012, 20:12   #194
ITTI
Пользователь
 
Регистрация: 19.12.2011
Сообщений: 65
По умолчанию

Цитата:
Сообщение от _Bers Посмотреть сообщение
Вектор векторов.
это подходит, ибо даже обычные массивы дядя еще не показывал.
но я почитаю вот там, попозже.
сейчас есть актуальней проблемы.
проверь, пожалуйста. оставляй замечания, исправлять буду сама. есть только два вопроса.
Код:
#include <iostream>
#include <cmath>
#include <vector>
using namespace std;
float s(float a, float b){
       float d = (b-a)*(b-a);
       return d;}
int main(){
    float x=0;// координаты
    float y=0;// точек
    
    vector<float> xx;
    vector<float> yy;
    float x1=0; float y1=0;
    float sum=0;
    int n; // кол-во точек
    cin >> n;
    for (int i=0; i<n; ++i){
        cin >> x; xx.push_back(x);
        cin >> y; yy.push_back(y);
        if (i>0 && i<n){
                x1=s(xx[i-1], xx[i]);
                y1=s(yy[i-1], yy[i]);
                sum += sqrt(x1+y1);// общее расстояние между точками
    }}
    x1=s(xx[n-1], xx[0]); // а вот эта часть как-то боком получилась
    y1=s(yy[n-1], yy[0]);
    sum += sqrt(x1+y1); 
    cout << sum << endl;
    system("pause");
    return 0;
}
1. что лучше для вещественного числа float или double?
2. как сделать что-бы sum округлялось до двух знаков после запятой(только попроще что-нибудь)?
ITTI вне форума Ответить с цитированием
Старый 13.01.2012, 20:40   #195
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от ITTI Посмотреть сообщение
это подходит, ибо даже обычные массивы дядя еще не показывал.
но я почитаю вот там, попозже.
сейчас есть актуальней проблемы.
проверь, пожалуйста. оставляй замечания, исправлять буду сама. есть только два вопроса.
Код:
#include <iostream>
#include <cmath>
#include <vector>
using namespace std;
float s(float a, float b){         
       float d = (b-a)*(b-a);
       return d;}
int main(){
    float x=0;// координаты
    float y=0;// точек
    
    vector<float> xx;       
    vector<float> yy;       
    float x1=0; float y1=0;
    float sum=0;
    int n; // кол-во точек
    cin >> n;
    for (int i=0; i<n; ++i){
        cin >> x; xx.push_back(x);
        cin >> y; yy.push_back(y);
        if (i>0 && i<n){                   //<---- Обрати внимание
                x1=s(xx[i-1], xx[i]);
                y1=s(yy[i-1], yy[i]);
                sum += sqrt(x1+y1);// общее расстояние между точками
    }}
    x1=s(xx[n-1], xx[0]); // а вот эта часть как-то боком получилась
    y1=s(yy[n-1], yy[0]);
    sum += sqrt(x1+y1); 
    cout << sum << endl;
    system("pause");
    return 0;
}
1. что лучше для вещественного числа float или double?
2. как сделать что-бы sum округлялось до двух знаков после запятой(только попроще что-нибудь)?
1. Грубо говоря double - тоже самое, что и float, только "двойной точности". Если ты не пишешь программу для высокоточных математических расчетов, то разницы особой нет.

2. Допустим, у тебя есть число: 123,12345
Тебе нужно, что бы в в результате после запятой осталось только две цыфры. Для этого:

123,12345*100 получаем 12312,345
Берём целую часть от полученного:

int val = (int) 12312,345

Так как приемник - целое, то дробная часть отрежеццо. Останется:
12312

Теперь делим на 100:

12312/100.0 получим: 123,12

Этот способ позволяет "отрезать" лишние цыфры.
То есть, правило "округления" тут не действует. Если тебе нужно именно огруглять - можно поюзать мат. библиотеку:

http://www.cplusplus.com/reference/clibrary/cmath/ceil/
http://www.cplusplus.com/reference/c...y/cmath/floor/

/ps приучай себя давать говорящие имена функциям и переменным. И не имей дурацкой привычки юзать условия в циклах, если эти условия могут быть истинными на всего одной итерации за все время жизни цикла. Это - не_рациональное падение производительности.

Последний раз редактировалось _Bers; 13.01.2012 в 21:05.
_Bers вне форума Ответить с цитированием
Старый 13.01.2012, 21:18   #196
ITTI
Пользователь
 
Регистрация: 19.12.2011
Сообщений: 65
По умолчанию

Цитата:
Сообщение от _Bers Посмотреть сообщение
Этот способ позволяет "отрезать" лишние цифры.
То есть, правило "округления" тут не действует. Если тебе нужно именно округлять - можно поюзать мат. библиотеку:
/ps приучай себя давать говорящие имена функциям и переменным. И не имей дурацкой привычки юзать условия в циклах, если эти условия могут быть истинными на всего одной итерации за все время жизни цикла.
имя дала нормальное. так там не один раз выполняется, а n-2.
может я не так поняла, но там округляется именно до целого числа.
так ответ получается правильный(два знака после запятой), но как-то тупо(?):
sum*=100;
sum=ceil(sum);
sum/=100;
cout << sum << endl;
ITTI вне форума Ответить с цитированием
Старый 13.01.2012, 22:00   #197
netrino
Участник клуба
 
Аватар для netrino
 
Регистрация: 15.07.2008
Сообщений: 1,933
По умолчанию

Цитата:
Сообщение от ITTI Посмотреть сообщение
как сделать что-бы sum округлялось до двух знаков после запятой(только попроще что-нибудь)?
Можно так:
Код:
double f = 2323.3214;
fixed(cout).precision(2);
cout << f << endl;
netrino вне форума Ответить с цитированием
Старый 14.01.2012, 06:21   #198
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от netrino Посмотреть сообщение
Можно так:
Код:
double f = 2323.3214;
fixed(cout).precision(2);
cout << f << endl;
Нельзя так. Вы не округлили число. f осталась без изменений.
_Bers вне форума Ответить с цитированием
Старый 14.01.2012, 06:56   #199
netrino
Участник клуба
 
Аватар для netrino
 
Регистрация: 15.07.2008
Сообщений: 1,933
По умолчанию

Цитата:
Сообщение от _Bers Посмотреть сообщение
Нельзя так. Вы не округлили число. f осталась без изменений.
А зачем его округлять до вывода? Округление ведь, в данном случае, делается, как я понял, исключительно для читабельности, посему нет необходимости менять саму f, достаточно вывести её в нужном формате.
netrino вне форума Ответить с цитированием
Старый 14.01.2012, 07:39   #200
_Bers
Старожил
 
Регистрация: 16.12.2011
Сообщений: 2,329
По умолчанию

Цитата:
Сообщение от ITTI Посмотреть сообщение
имя дала нормальное. так там не один раз выполняется, а n-2.
может я не так поняла, но там округляется именно до целого числа.
так ответ получается правильный(два знака после запятой), но как-то тупо(?):
sum*=100;
sum=ceil(sum);
sum/=100;
cout << sum << endl;
Кэп, я нефига ничего не понял. Если нужно заполнить массив точками, и подсчитать сумму расстояний между этими точками, то вот например:

Код:
#include <math.h>
#include <iostream>

int Random(int least, int greatest) //генератор псевдо случайных чисел
{
    static int seed(  (srand(  (size_t)time(NULL)  ), 0)  );    //инициализируется только один раз 
    return rand() % (greatest - least) + least;
}


struct SFlCoord { float x,y; }; //двух-мерные координаты
                                         //Олицетворяет собой точку

float DistancePoint(const SFlCoord& Point1, const SFlCoord& Point2);
//Функция принимает в качестве аргументов две точки, и возвращает расстояние между ними

void AddPoint(std::vector<SFlCoord>& crc);
//Функция принимает на входе ссылку на вектор, и добавляет в него новую точку. 
//Координаты точки задаются случайным образом 
//(Потому что реально лень, каждый раз дел это в ручную с клавиатуры)

void GeneratePointArray(const size_t sizeArr, std::vector<SFlCoord>& crc, float& totalSumm);
//Функция заполняет вектор случайными точками, и заодно подсчитывает сумму растояний между этими точками
//sizeArr - количество точек, которое нужно поместить в вектор
//crc - вектор, в который будут записаны точки
//totalSumm - сюда запишется сумма расстояний между этими точками


int main()
{
    using namespace std;
    std::vector<SFlCoord> myPoints; //вектор точек
    float sum=0;                    //общая дистанция между двумя точками
    
    //на этапе тестирования автоматизируем процесс ввода исходных данных
    
    int n = Random(3,10);                        //количество точек будет заданно случайно
    cout << "Общее количество точек: "<<n<<endl;
    
    GeneratePointArray(n, myPoints,sum);          //координаты точек будут заданы случайно


    sum = ((float)((int) (sum *=100)))/100.0f; //обрезание 
    
    cout << "общее расстояние между точками: "<< sum << endl;
    return 0;
}


float DistancePoint(const SFlCoord& Point1, const SFlCoord& Point2) //расстояние между точками
{
    float distanceX = (Point2.x-Point1.x)*(Point2.x-Point1.x);
    float distanceY = (Point2.y-Point1.y)*(Point2.y-Point1.y);
    float distPoint = sqrt(distanceX+distanceY);

    return distPoint;
}

void AddPoint(std::vector<SFlCoord>& crc) //добавит точку со случайными координатыми в вектор
{ 
    SFlCoord NewPoint;  int minP=0; int maxP=10;
    NewPoint.x= (float) Random(minP,maxP);  
    NewPoint.y= (float) Random(minP,maxP); 
    crc.push_back(NewPoint);
}

void GeneratePointArray(const size_t sizeArr, std::vector<SFlCoord>& crc, float& totalSumm)
{
    using namespace std;
    crc.clear();  crc.reserve(sizeArr);  totalSumm=0; //подготовка выходных данных
    
    AddPoint(crc);  //добавим первую случайнйю точку в вектор
    cout << "Точка №0 x = "<< crc[0].x<<" : y = "<< crc[0].y<<endl;
    
    for(size_t i=1; i< sizeArr; ++i)
    {
        const SFlCoord& Point1= crc.back(); //запомним координаты предыдущей точки

        AddPoint(crc); //добавим очередную случайную точку в вектор

        const SFlCoord& Point2= crc.back(); //запомним координаты этой очередной точки
        
        totalSumm +=DistancePoint(Point2, Point1); //выясним расстояние между очередной и предыдущей точками
                                                   //и увеличим счетчик суммы

        cout << "Точка №"<<i<<" x = "<< Point2.x<<" : y = "<< Point2.y;
        cout << " Общая дистанция = "<<totalSumm<<endl;
    }
}
/зы На этапе разработки и тестирования частенько приходится по многу раз перезапускать приложение. Чего то там корректировать, запускать снова. Если ты каждый раз будешь заново все исходные данные вводить в ручную - ты до второго пришествия с отладкой не закончишь.

На этапе тестирования и отладки нужно стремится делать так, что бы все исходные данные забивались автоматически.

Последний раз редактировалось _Bers; 14.01.2012 в 07:48.
_Bers вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
PopupMenu со мной не дружит Жигилий_Ульяна Компоненты Delphi 5 25.12.2008 11:04
проблемы с select или со мной... smoke888 JavaScript, Ajax 2 23.09.2008 19:02