Форум программистов, компьютерный форум CyberForum.ru

Разложить число на сумму степеней двойки - C++

Восстановить пароль Регистрация
 
Рейтинг: Рейтинг темы: голосов - 24, средняя оценка - 4.88
Tiva
94 / 94 / 1
Регистрация: 25.04.2012
Сообщений: 429
27.09.2012, 08:48     Разложить число на сумму степеней двойки #1
помогите написать функцию, раскладывающую число на сумму степеней двойки.

т.е. у меня есть 6 прав у пользователей, которые пронумерованы степенями двойки

создание объекта 2
создание субъекта 4
удаление объекта 8
удаление субъекта 16
внесение прав 32
удаление прав 64

т.е. суперпользователь имеет доступ 126(сумма всех степеней),
другой пользователь имеет доступ 10 (создание и удаление только объектов)
третий 36 (создание субъекта и внесение прав)

помогите написать функцию, возвращающую список доступных действий пользователю.
сам что-то пробовал, но даже стыдно выкладывать бред, который я писал
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
SatanaXIII
Супер-модератор
Эксперт С++
 Аватар для SatanaXIII
5549 / 2563 / 233
Регистрация: 01.11.2011
Сообщений: 6,337
Завершенные тесты: 1
27.09.2012, 09:40     Разложить число на сумму степеней двойки #2
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#include<math> 
 
int dostup = 126;
for(int i=6; i>=1; i--)
  {
  Memo1->Lines->Add(pow(2,i));
  if(dostup>=pow(2,i))
    {
    dostup -= pow(2,i);
 
    switch((int)pow(2,i))
      {
      case 2  : Memo1->Lines->Add("создание объекта"); break;
      case 4  : Memo1->Lines->Add("создание субъекта"); break;
      case 8  : Memo1->Lines->Add("удаление объекта"); break;
      case 16 : Memo1->Lines->Add("удаление субъекта"); break;
      case 32 : Memo1->Lines->Add("внесение прав"); break;
      case 64 : Memo1->Lines->Add("удаление прав"); break;
      }
 
    }
  }
diagon
Higher
 Аватар для diagon
1920 / 1186 / 49
Регистрация: 02.05.2010
Сообщений: 2,925
Записей в блоге: 2
27.09.2012, 09:47     Разложить число на сумму степеней двойки #3
Цитата Сообщение от SatanaXIII Посмотреть сообщение
pow(2,i)
зачем использовать pow, если есть битовый сдвиг?
C++
1
1 << i
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
27.09.2012, 09:59     Разложить число на сумму степеней двойки #4
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
int x;
int i;
size_t s=sizeof(x)*CHAR_BIT;
int mask;
cin>>x;
cout<<endl<<x<<"=";
mask=(1<<s-1);
if (x&mask)
{
 cout<<"2^"<<s;
}
for (i=s-2, mask>>=1; i>=0; --i, mask>>=1)
{
 if (x&mask)
 {
  cout<<"+2^"<<i;
 }
}
if (x==0)
{
 cout<<0; 
}
cout<<endl;
SatanaXIII
Супер-модератор
Эксперт С++
 Аватар для SatanaXIII
5549 / 2563 / 233
Регистрация: 01.11.2011
Сообщений: 6,337
Завершенные тесты: 1
27.09.2012, 10:06     Разложить число на сумму степеней двойки #5
Цитата Сообщение от diagon Посмотреть сообщение
зачем использовать pow, если есть битовый сдвиг?
Это мое дизайнерское видиние.


taras atavin, и чей код нагляднее?
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
27.09.2012, 10:06     Разложить число на сумму степеней двойки #6
Цитата Сообщение от SatanaXIII Посмотреть сообщение
taras atavin, и чей код нагляднее?
да куда уж нагляднее?
SatanaXIII
Супер-модератор
Эксперт С++
 Аватар для SatanaXIII
5549 / 2563 / 233
Регистрация: 01.11.2011
Сообщений: 6,337
Завершенные тесты: 1
27.09.2012, 10:16     Разложить число на сумму степеней двойки #7
Цитата Сообщение от taras atavin Посмотреть сообщение
да куда уж нагляднее?
Ну вам просто завидно, признайте.
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
27.09.2012, 10:36     Разложить число на сумму степеней двойки #8
Чему здесь завидовать? Ни о чём не говорящему пову? Бред, кобыла отдыхает. А у меня маска бита и перебор битов.
zitxbit
Master C/C++
 Аватар для zitxbit
86 / 738 / 75
Регистрация: 11.04.2012
Сообщений: 971
27.09.2012, 10:36     Разложить число на сумму степеней двойки #9
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
#include <stdio.h>
#include <conio.h>
#include <math.h>
#include <locale.h>
 
#include <iostream>
 
#define bit(reg,n) reg & (_int64)pow(2.,n) ? 1 : 0 \
 
using namespace std;
 
int main()
{
    setlocale(LC_ALL,"Russian");
 
    _int64 N = 0xFFFFFFFFFFFFFFFF; // superuser
    for (int r = 0; r <= 64; r++)
    {
        if (!bit(N, r)) continue;
 
        switch (r)
        {
            case 2:  cout << "создание объекта" << endl; break;
            case 4:  cout << "создание субъекта" << endl; break;
            case 8:  cout << "удаление объекта" << endl; break;
            case 16: cout << "удаление субъекта" << endl; break;
            case 32: cout << "внесение прав" << endl; break;
            case 64: cout << "удаление прав" << endl; break;
        }
    }
 
    _getch();
 
    return 0;
}
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
27.09.2012, 10:43     Разложить число на сумму степеней двойки #10
Ну, если охота текстом, то можно так:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
void PrivelegesByText(uint_8t Privilages)
{
 static char[8][32]={"", "создание объекта", "создание субъекта", "удаление объекта", "удаление субъекта", "внесение прав", "удаление прав", ""}
 size_t i;
 uint_8t mask;
 for (i=7, mask=1<<7; i>=0; --i, mask>>=1)
 {
  if (x&mask)
  {
   cout<<s[i]<<endl;
  }
 }
}
SatanaXIII
Супер-модератор
Эксперт С++
 Аватар для SatanaXIII
5549 / 2563 / 233
Регистрация: 01.11.2011
Сообщений: 6,337
Завершенные тесты: 1
27.09.2012, 10:49     Разложить число на сумму степеней двойки #11
taras atavin, ой ну да ладно вам заводиться-то. Я имею ввиду, что мне дозволено постить говно, а вам нет, в виду вашего высокого уровня.

Цитата Сообщение от taras atavin Посмотреть сообщение
Ну, если охота текстом, то можно так:
Бесспорно это гораздо лучше.
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
27.09.2012, 11:02     Разложить число на сумму степеней двойки #12
Цитата Сообщение от SatanaXIII Посмотреть сообщение
постить говно,
не вижу его в теме.
ValeryS
Модератор
6377 / 4843 / 442
Регистрация: 14.02.2011
Сообщений: 16,058
27.09.2012, 11:09     Разложить число на сумму степеней двойки #13
слушайте а нахрена здесь цикл и switch ???
один пользователь может иметь несколько прав
просто набор if
C++
1
2
3
4
5
6
7
8
9
10
11
12
if(dostup&2) 
 Memo1->Lines->Add("создание объекта");
if(dostup& 4) 
  Memo1->Lines->Add("создание субъекта");
if(dostup& 8) 
 Memo1->Lines->Add("удаление объекта"); 
if(dostup& 16) 
 Memo1->Lines->Add("удаление субъекта");
if(dostup& 32)
 Memo1->Lines->Add("внесение прав");
if(dostup& 64)
 Memo1->Lines->Add("удаление прав");
SatanaXIII
Супер-модератор
Эксперт С++
 Аватар для SatanaXIII
5549 / 2563 / 233
Регистрация: 01.11.2011
Сообщений: 6,337
Завершенные тесты: 1
27.09.2012, 11:57     Разложить число на сумму степеней двойки #14
ValeryS,
Tiva
94 / 94 / 1
Регистрация: 25.04.2012
Сообщений: 429
12.11.2012, 13:51  [ТС]     Разложить число на сумму степеней двойки #15
Цитата Сообщение от ValeryS Посмотреть сообщение
слушайте а нахрена здесь цикл и switch ???
один пользователь может иметь несколько прав
просто набор if
C++
1
2
3
4
5
6
7
8
9
10
11
12
if(dostup&2) 
 Memo1->Lines->Add("создание объекта");
if(dostup& 4) 
  Memo1->Lines->Add("создание субъекта");
if(dostup& 8) 
 Memo1->Lines->Add("удаление объекта"); 
if(dostup& 16) 
 Memo1->Lines->Add("удаление субъекта");
if(dostup& 32)
 Memo1->Lines->Add("внесение прав");
if(dostup& 64)
 Memo1->Lines->Add("удаление прав");
C++
1
2
3
4
5
6
7
8
9
void Matrix::Command(int right)
{
    if(right & ADD_OBJ) cout<<"1 - создать объект\t";
    if(right & ADD_SUB) cout<<"2 - создать субъект\t";
    if(right & DEL_OBJ) cout<<"3 - удалить объект\n";
    if(right & DEL_SUB) cout<<"4 - удалить субъект\t";
    if(right & ADD_RIGHT) cout<<"5 - добавить право\t";
    if(right & DEL_RIGHT) cout<<"6 - удалить право\n";
}
сделал под консоль, передаю в метод права. передаю 14 (2+4+8, т.е. должен вывести первые три), выводит все равно все шесть.
ADD_OBJ ADD_SUB и тд объявлены как
C++
1
2
#define ADD_OBJ 2 
#define ADD_OBJ 4
Добавлено через 8 минут
Цитата Сообщение от SatanaXIII Посмотреть сообщение
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#include<math> 
 
int dostup = 126;
for(int i=6; i>=1; i--)
  {
  Memo1->Lines->Add(pow(2,i));
  if(dostup>=pow(2,i))
    {
    dostup -= pow(2,i);
 
    switch((int)pow(2,i))
      {
      case 2  : Memo1->Lines->Add("создание объекта"); break;
      case 4  : Memo1->Lines->Add("создание субъекта"); break;
      case 8  : Memo1->Lines->Add("удаление объекта"); break;
      case 16 : Memo1->Lines->Add("удаление субъекта"); break;
      case 32 : Memo1->Lines->Add("внесение прав"); break;
      case 64 : Memo1->Lines->Add("удаление прав"); break;
      }
 
    }
  }
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
void Matrix::Command(int right)
{
    //int right = 126;
    for(int i=6; i>=1; i--)
    {
        //Memo1->Lines->Add(pow(2,i));
        if(right>=pow(2.,(int)i))
        {
            right -= pow(2.,(int)i);
    switch((int)pow(2.,i))
      {
          case 2  : cout<<"создание объекта\t"; break;
          case 4  : cout<<"создание субъекта\t"; break;
          case 8  : cout<<"удаление объекта\n"; break;
          case 16 : cout<<"удаление субъекта\t"; break;
          case 32 : cout<<"внесение прав\t"; break;
          case 64 : cout<<"удаление прав\n"; break;
      }
    }
  }
}
то же не работает (( блин, помогите!

Добавлено через 14 минут
Цитата Сообщение от taras atavin Посмотреть сообщение
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
int x;
int i;
size_t s=sizeof(x)*CHAR_BIT;
int mask;
cin>>x;
cout<<endl<<x<<"=";
mask=(1<<s-1);
if (x&mask)
{
 cout<<"2^"<<s;
}
for (i=s-2, mask>>=1; i>=0; --i, mask>>=1)
{
 if (x&mask)
 {
  cout<<"+2^"<<i;
 }
}
if (x==0)
{
 cout<<0; 
}
cout<<endl;
на выходе выдает не правильно:
Код
12

12=+2^3+2^2+2^1+2^0
8+4+2+1 не равно 15..
к сожалению я совсем не понимаю значения битовых сдвигов и т.д. и не могу даже понять в чем ошибка Вашего алгоритма
taras atavin
Ушёл с форума.
 Аватар для taras atavin
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
12.11.2012, 14:10     Разложить число на сумму степеней двойки #16
Цитата Сообщение от ValeryS Посмотреть сообщение
слушайте а нахрена здесь цикл и switch ???
один пользователь может иметь несколько прав
просто набор if
Набор ифов очень плохо расширяется на другую разрядность, а растёт быстро. Большая же программа при прочих равных работает медленнее, так как чаще подгружается из основной оперативной памяти в кеш и с диска в оперативную память. Этого надо избегать, если только у тебя не упакованные флаги. Хотя, в данном случае вроде они.
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
12.11.2012, 14:21     Разложить число на сумму степеней двойки
Еще ссылки по теме:

C++ является ли число суммой степеней двойки?
C++ Вывести таблицу степеней двойки от нулевой до десятой
C++ программа, которая выводит таблицу степеней двойки от нулевой до десятой

Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
Tiva
94 / 94 / 1
Регистрация: 25.04.2012
Сообщений: 429
12.11.2012, 14:21  [ТС]     Разложить число на сумму степеней двойки #17
ааа люди я дико извиняюсь, все работает!! я случайно передавал не то значение в функцию, передавал уровень доступа из файла, а для отладки менял значение из матрицы!! т.е. в функцию всегда передавалось одно и тоже при всех моих изменениях! все работает!!
Yandex
Объявления
12.11.2012, 14:21     Разложить число на сумму степеней двойки
Ответ Создать тему
Опции темы

Текущее время: 16:38. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru