Вам присваивается целое число 51234
(скажем), нам нужно отсортировать цифры номера, который будет выводиться 12345
.
Как это сделать без использования массива?
Вам присваивается целое число 51234
(скажем), нам нужно отсортировать цифры номера, который будет выводиться 12345
.
Как это сделать без использования массива?
Вы можете использовать цикл и % 10
для извлечения каждой цифры.
Внешний цикл от 0 до 9 может использоваться для проверки наличия цифры. Если он существует, распечатайте его.
В псевдокоде:
n = integer // 51234
FOR digit = 0 TO 9
temp = n
REPEAT
IF temp % 10 = digit THEN PRINT digit
temp /= 10
UNTIL temp = 0
Изменить: Этот тест в gcc показывает, что он обрабатывает нули и повторяющиеся цифры:
$ cat sortdigits.c
#include <stdio.h>
main () {
int n,digit,temp;
n = 43042025;
for (digit=0;digit<9;digit++)
for (temp=n;temp>0;temp/=10)
if (temp%10==digit) printf("%d",digit);
printf("\n");
}
$ ./sortdigits
00223445
// Bubblesort
long sortNum(long n) {
while (true) {
long a = n % 10, p = 9;
bool s = false;
for (long r = n / 10; r; r/= 10) {
long b = r % 10;
if (a < b) {
n -= p * (b - a);
s = true;
} else a = b;
p *= 10;
}
if (!s) return n;
}
}
#include <iostream>
int main(int argc, char **argv) {
if (argc > 1) {
long n = strtol(argv[1], 0, 0);
std::cout << "Unsorted: " << n << std::endl;
n = sortNum(n);
std::cout << "Sorted: " << n << std::endl;
}
return 0;
}
$ g++ -Wall -Wextra bubble-int.cpp && ./a.exe 183974425
Unsorted: 183974425
Sorted: 123445789
Общий обзор:
Единственным потенциально сложным битом может быть правильная обработка нулей - вам не нужно слишком много, и вам нужно будет обрабатывать край, где вход нуль правильно.
Фактическая реализация остается в виде упражнения...
Легко:
#include <stdio.h>
#include <stdlib.h>
static void pput(int n, int c)
{
int i;
for (i=0; i < n; ++i) putchar(c);
}
int main(int argc, char *argv[])
{
int zeros = 0;
int ones = 0;
int twos = 0;
int threes = 0;
int fours = 0;
int fives = 0;
int sixes = 0;
int sevens = 0;
int eights = 0;
int nines = 0;
long num = 0;
if (argc > 1) {
char *eptr;
num = strtol(argv[1], &eptr, 0);
if (*eptr) {
fprintf(stderr, "Invalid number: '%s', using 0.\n", argv[1]);
num = 0;
}
}
do {
switch (num % 10) {
case 0: ++zeros;
break;
case 1: ++ones;
break;
case 2: ++twos;
break;
case 3: ++threes;
break;
case 4: ++fours;
break;
case 5: ++fives;
break;
case 6: ++sixes;
break;
case 7: ++sevens;
break;
case 8: ++eights;
break;
case 9: ++nines;
break;
default:
break;
}
} while ((num /= 10));
pput(zeros, '0');
pput(ones, '1');
pput(twos, '2');
pput(threes, '3');
pput(fours, '4');
pput(fives, '5');
pput(sixes, '6');
pput(sevens, '7');
pput(eights, '8');
pput(nines, '9');
putchar('\n');
return 0;
}
Компиляция и запуск:
$ gcc -Wextra -Wall -ansi -pedantic -Wfloat-equal -Wundef -Wshadow \
-Wpointer-arith -Wcast-qual -Wcast-align -Wstrict-prototypes \
-Wswitch-default -Wswitch-enum -Wstrict-overflow=5 \
-Wdeclaration-after-statement -Wwrite-strings -Wconversion \
-Waggregate-return -Wunreachable-code a.c
$ ./a.out
0
$ ./a.out 54321
12345
$ ./a.out 9834346
3344689
$ ./a.out hello
Invalid number: 'hello', using 0.
0
: -)
Другое решение, не использующее массивы, и довольно короткое количество строк:
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
int main(int argc, char *argv[])
{
long num = 0;
int i;
size_t *freq;
if (argc > 1) {
char *eptr;
num = strtol(argv[1], &eptr, 0);
if (*eptr || errno == ERANGE) {
fprintf(stderr, "Invalid number: '%s', using 0.\n", argv[1]);
num = 0;
}
}
if ((freq = calloc(10, sizeof *freq)) == NULL) {
perror("malloc failure");
return EXIT_FAILURE;
}
do
++freq[num % 10];
while ((num /= 10));
for (i=0; i < 10; ++i) {
size_t j;
for (j=0; j < freq[i]; ++j)
putchar(i + '0');
}
putchar('\n');
free(freq);
return EXIT_SUCCESS;
}
Да, я знаю о "правильном" решении. Но почему бы не использовать массивы для этой проблемы? Как сказал один из комментаторов, я бы не хотел работать в компании, которая не позволяла мне использовать массивы в C.
Вам вообще не нужно писать программу, просто сделайте это с помощью команд оболочки:
echo "51234" | sed 's+\(.\)+\1\n+g' | sort | tr -d '\n'
Разделить на 10 заданных целых чисел в цикле. Распечатайте напоминание на каждой итерации.
Или "сортировка" означает, что здесь? Для реальной сортировки вам понадобятся две петли. Один из них будет от 0 до 9. Еще один будет описан ранее.
int main()
{
int x = 0;
cin >> x;
for ( int l = 0; l < 10; ++l )
{
int rem = x % 10;
int tx = x / 10;
while ( rem || tx )
{
if ( rem == l ) cout << rem;
rem = tx % 10;
tx = tx / 10;
}
}
cout << endl;
}
Уверенные массивы отсутствуют, но у нас есть лучший контейнер:
void foo(unsigned i) {
std::set<char> digits;
do {
digits.insert(`0` + i % 10);
i /= 10;
while(i!=0);
}
Используйте multiset
, если ваш ввод содержит цифры типа 887
, которые должны быть напечатаны как 788
Можно попробовать что-то вроде сортировки вставки. По существу, создайте новый номер, взяв одну цифру из старой за раз и положив ее в нужное место. Что-то вроде этого.
while(num!=0){
dig = num%10; // get the last digit
if(newNum=0 ) newNum+=dig;
else{
newNumTemp = 0; flag =1;i =1;
while (newNum != 0){
Newdig = newNum%10;
if(flag){
if (Newdig >= dig )
{NewNumTemp = Newdig*(10^i)+ NewNumTemp; }
else { flag=0; NewNumTemp = dig*(10^i) +NewNumTemp; i++;NewNumTemp = Newdig* (10^i)+ NewNumTemp;}
} // end of outer if
i++;
newNum/=10;
} // end of while
newNum= newNumTemp;
}// end of else
num/=10;
}// end of outer while
Создайте контейнерный интерфейс над int (что-то вроде вектора), где оператор ссылается на десятичную цифру i-го. Вам придется определять итераторы и другие вещи. Затем вызовите std:: sort.;)