FreeNOS
SievePrime.cpp
Go to the documentation of this file.
1/*
2 * Copyright (C) 2015 Niek Linnenbank
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include <stdio.h>
19#include <string.h>
20#include <stdlib.h>
21#include <String.h>
22#include <unistd.h>
23#include <math.h>
24#include <errno.h>
25#include "SievePrime.h"
26
27SievePrime::SievePrime(int argc, char **argv)
28 : POSIXApplication(argc, argv)
29{
30 parser().setDescription("Compute prime numbers using the Sieve of Eratosthenes algorithm");
31 parser().registerPositional("NUMBER", "Maximum number to search for prime numbers");
32 parser().registerFlag('o', "stdout", "Write results to standard output if set");
33}
34
38
40{
41 u8 *map;
42 int n, k = 2, i, last, sqrt_of_n;
43 Size resultsWritten = 0;
44
45 // Read max number
46 n = atoi(arguments().get("NUMBER"));
47 sqrt_of_n = sqrt(n);
48
49 // Try to allocate memory
50 if ((map = (u8 *) malloc(n * sizeof(u8))) == NULL)
51 {
52 ERROR("malloc failed: " << strerror(errno));
53 return IOError;
54 }
55
56 // Set to true
57 for (i = 0; i < n; i++)
58 map[i] = 1;
59
60 // Find all primes below sqrt(n) sequentially
61 searchSequential(sqrt_of_n, map);
62
63 // Now continue above sqrt(n) sequentially
64 while (k < sqrt_of_n)
65 {
66 // Prime number?
67 if (!map[k])
68 {
69 k++;
70 continue;
71 }
72
73 // Mark multiples of k in my range
74 i = sqrt_of_n;
75 last = n;
76
77 while (i < last)
78 {
79 // Do we need to unmark this number? (no prime)
80 if (!(i % k))
81 map[i] = 0;
82
83 i++;
84 }
85 // Look for the next prime
86 k++;
87 }
88
89 reportResult(n, map, resultsWritten);
90 write(1, "\r\n", 2);
91
92 // Done
93 return Success;
94}
95
97 const u8 *map,
98 Size & resultsWritten,
99 const Size offsetNumber) const
100{
101 // Print the result
102 if (arguments().get("stdout"))
103 {
105
106 for (int i = 0; i < n; i++)
107 {
108 if (map[i] == 1)
109 {
110 output << " " << (i + offsetNumber);
111 resultsWritten++;
112 }
113
114 if (resultsWritten >= 32)
115 {
116 output << "\r\n";
117 write(1, *output, output.length());
118 output = "";
119 resultsWritten = 0;
120 }
121 }
122
123 if (output.length() > 0)
124 {
125 write(1, *output, output.length());
126 }
127 }
128
129 return Success;
130}
131
133 u8 *map) const
134{
135 int i, j;
136
137 // Sequential algorithm
138 // Next is a prime
139 for (i = 2; i < n; i++)
140 {
141 // Prime number?
142 if (map[i])
143 {
144 // Mask off all multiples
145 for (j = i + 1; j < n; j++)
146 {
147 if (!(j % i))
148 map[j] = 0;
149 }
150 }
151 }
152
153 return Success;
154}
Result
Result codes.
Definition Application.h:54
const ArgumentContainer & arguments() const
Get program arguments.
ArgumentParser & parser()
Get program arguments parser.
void setDescription(const String &desc)
Set program description.
Result registerPositional(const char *name, const char *description, Size count=1)
Register a positional argument.
Result registerFlag(char arg, const char *name, const char *description)
Register a flag Argument.
POSIX-compatible application.
virtual Result output(const char *string) const
Print text to output.
Result reportResult(const int n, const u8 *map, Size &resultsWritten, const Size offsetNumber=0) const
Report the calculated results.
Result searchSequential(const int n, u8 *map) const
Perform sequential search for prime numbers.
virtual ~SievePrime()
Destructor.
SievePrime(int argc, char **argv)
Constructor.
virtual Result exec()
Execute the application.
Abstraction of strings.
Definition String.h:42
C int atoi(const char *nptr)
Convert a string to an integer.
Definition atoi.cpp:21
C u32 sqrt(u32 number)
Compute the square root of a number.
Definition sqrt.cpp:20
C char * strerror(int errnum)
The strerror function maps the number in errnum to a message string.
Definition strerror.cpp:20
C int errno
The lvalue errno is used by many functions to return error values.
C void * malloc(size_t size)
A memory allocator.
Definition malloc.cpp:22
C ssize_t write(int fildes, const void *buf, size_t nbyte)
Write on a file.
Definition write.cpp:22
#define NULL
NULL means zero.
Definition Macros.h:39
#define ERROR(msg)
Output an error message.
Definition Log.h:61
unsigned int Size
Any sane size indicator cannot go negative.
Definition Types.h:128
unsigned char u8
Unsigned 8-bit number.
Definition Types.h:59