FAQ:ANSI CPP

Материал из Весельчак У
Версия от 21:25, 8 апреля 2008; RXL (обсуждение | вклад) (Категория FAQ)

(разн.) ← Предыдущая | Текущая версия (разн.) | Следующая → (разн.)
Перейти к: навигация, поиск

Содержание

Не получается сравнить два числа типа double

стандартный прием - задание точности:

	#include <math.h>
	double d1,d2;
	double acc=0.00001;//требуемая точность сравнения
	...
	...
	if( fabs(d1-d2) < acc )
	{
		//операнды равны (с точностью acc)
	}
	else
	{
		//убедились, что операнды не равны, здесь можно
		//смело сравнивать операторами ">" и "<"
	}

Как задать число знаков после запятой у float при преобразовании в строку?

примеры для разных случаев:

	char sDouble[128]
	float d1 = 0.001778;
	...
	sprintf(sDouble,"%.4f",d1);//4 знака после запятой
	...
	printf("%.4f", d1);//4 знака после запятой
	...
	cout<<setiosflags( ios::fixed )<< setprecision( 4 )
					<< d1;//4 знака после запятой

Как динамически задать число знаков после запятой у float при преобразовании в строку?

Если нужно вывести, к примеру, double с 5 знаками после десятичной точки, сначала нужно сформировать строку вида "%.5f", а потом задать ее в качестве спецификации формата

	char sDouble[128], strFormat[128];
	double d1 = 150.0f;
	int nCount;//текущее количество знаков после запятой
	...
	nCount = 5;
	sprintf(strFormat, "%%.%df", nCount );
	//strFormat теперь содержит строку "%.5f"
	//форматируем:
	sprintf(sDouble, strFormat, d1);

аналогично, если используется класс CString :

	CString sDouble,strFormat;
	...
	strFormat.Format("%%.%df", nCount );
	sDouble.Format(strFormat, d1);

Как задать число знаков после запятой у float в функции printf?

В printf в спецификаторе числа разрядов можно поставить символ "*". тогда соответствующий по порядку аргумент будет интерпретирован

как число знаков
	printf("%.*f", 2, 3.1415);//выведет 3.14 

(для CString::Format символ "*" НЕ работает)

Как всё, что выводится в cout,вывести в файл?

Можно перенаправишь поток cout при запуске программы, но тогда ВСЕ сообщения пойдут в этот файл. Так что лучше открыть специальный поток для файла:

	#include <fstream>
	...
	ofstream file_out (filename);
	...
	file_out<< "текст" <<setiosflags( ios::fixed )
					<<setprecision( 3 )<< 3.456564 << endl;

Как преодолеть такую ситуацию, когда при вводе текста в переменную считываются только те символы, которые шли до пробела, а мне необходимо считать всю строку целиком?

например:

	char test1[20],test[20];
	cin>>test;	//ввожу: "текст с пробелом"
	cout<<test;	//выводится: "текст"}

	scanf("%s",test1);	//ввожу: "текст с пробелом"
	printf("%s",test1); //выводится: "текст"

Как это обойти? Средствам доступными в TC++3?

	string buffer;
	getline(cin, buffer, '\n');
	cout << buffer << "|" << endl;

или

	do
	{
		ch = getch();
		cout << ch
	}while(ch!='/0');

Какую функцию нужно использовать для генерации случайных чисел от 0 до 1?

	#include <climits>
	...
	double betweenZeroAndOne = double(rand()) / double(INT_MAX);

Почему не получается присвоить строку?

Например я пишу:


	char mess[]="";
	...
	mess="мой текст";//задаю значение строки
	MessageBox(hwnd, mess,"Error Message",MB_OK);

Ответ: Массив mess объявлен как

  char mess[]="";

то есть всё равно что

  char mess[1]='\0';

размер массива равен единице, первый элемент равен 0.

Чтобы присвоить строку, нужно увеличить размер массива (см. пример) и использовать strcpy для копирования содержимого "мой текст" в mess :


	char mess[100];
	mess[0]=0;//инициализация
	...
	strcpy(mess, "мой текст");

Либо использовать std::string (стандартный класс работы со строками в C++).

Как из конструктора класса-наследника передать параметры конструктору базового класса?


	//базовый класс
	class parent
	{
		public:
		parent(int n)
		{
		}
	};

	//наследник
	class child: public parent
	{
		child(int n,double d): parent(n)
		{
		}
	};

как обратиться к переменной или методу базового класса?

если не вдаваться в права доступа (public,private,protected), то так <имя_базового_класса>::переменная; <имя_базового_класса>::метод();

class Cbase
{
protected:
	int metod()
	{
		return 1;
	}
};
	
class Cchild:public Cbase
{
	int metod()
	{
		return 5;
	}
	
	void example()
	{
		int n;
		
		//вызов Cchild::metod()
		n=metod();
	
		//вызов Cbase::metod()
		n=Cbase::metod();
	}
};

Стандартный генератор псевдослучайных чисел.

Алгоритм генератора псевдослучайных чисел, который поставляется вместе с стандартными библиотеками С

#define RAND_MAX 32767

unsigned long next=1;

int rand(void) {
 next=next*1103515245+12345;
 return((unsigned int)(next/65536)%32768);
}

void srand(unsigned int seed) {
 next=seed;
}

Источник: http://algolist.manual.ru/maths/generator/standard.php

Как проинициализировать статический мембер класса?

class A
{
	const static int m_n;
	const static int m_Arr[];
};
	
const int A::m_n=0;
const int A::m_Arr[] ={1, 2, 5, 10, 20};

Как задать значение константы в двоичном представлении (т.е. единицами и нулями в виде битового поля)?

можно использовать макросы, например:

//МАКРОСЫ ДЛЯ ДВОИЧНЫХ ЧИСЕЛ
	
//байт
#define _b8(b) ((BYTE)(\
	(b&0x10000000?0x80:0)|(b&0x01000000?0x40:0)|\
	(b&0x00100000?0x20:0)|(b&0x00010000?0x10:0)|\
	(b&0x00001000?0x08:0)|(b&0x00000100?0x04:0)|\
	(b&0x00000010?0x02:0)|(b&0x00000001?0x01:0)))
//слово
#define __b16(b16)	((WORD)((_b8(((unsigned __int64)b16)>>32)<<8)|(_b8(b16))))
//двойное слово
#define __b32(b16H,b16L)	((DWORD)(((__b16(b16H))<<16)|(__b16(b16L))))
	
	
	
//пример:
BYTE by;
by=_b8(0x01010110);//	==0x56
by=_b8(0x111);//	==7
	
WORD w;
w=__b16(0x0111011011010011);//==0x76d3
	
DWORD dwd;
dwd=__b32(0x0101010110110011,0x0101111011010001);//==0x55B35ED1
dwd=__b32(0x1000101110101010,0x11010101);//==0x8BAA00D5

Как можно число, представленное в символьном виде, получить (или преобразовать) в виде целочисленного типа данных? И как представить число в виде массива символов (строки)? (например CString -> int и int -> CString)

CString txt;
int n;
...
txt="1234";
n=atoi(txt); //CString -> int
...
n=1234;
txt.Format("%d",n);//  int -> CString