Regular Expression for any number divisible by 60 using C# .Net? - c#

I need to apply validation on input time intervals that are taken in as seconds. Now i am not really good at Regular expressions. So can any body help making a regular expression that can test whether a number is divisible by 60.
I was wondering if i could use to test one that check that the number is divisible by 10 and then check whether the same is divisible by 6.
For number divisible by 10 here [\d*0] is the expression i guess. Please correct me if i am wrong.
Hope somebody solves my problem.
Thanks

Why not do N % 60 ?
Why you want to use regex for a job which can easily be done using one operator ?

As others have mentioned, regular expressions are completely the wrong tool to use for this. Rather, use TryParse to convert the string to an integer, and then test whether the integer is divisible by 60.
That said, it is instructive to see how this could possibly work with a regexp.
First off, of the one-digit numbers, only 0 is evenly divisible by 60. Of the non-one-digit numbers, all numbers divisible by 60 are also divisible by 20, and therefore end in 00, 20, 40, 60 or 80. That is easily tested with a regexp.
Suppose it passes the first test. We know from this test that the number is divisible by 20. Now all we need to do is show that it is divisible by 3. If it is, then it is divisible by both 20 and 3 and therefore must be divisible by 60, since 20 and 3 are coprime.
So we need a regular expression that can determine if a number is divisible by 3.
It is well known that numbers divisible by three are such that the sum of their digits is divisible by 3.
It is also well known that every regular expression corresponds to a finite state machine, and every finite state machine corresponds to a regular expression.
Therefore if we can come up with a finite state machine that determines divisibility by three, we're done.
This is easily done. Our finite state machine has three states, A, B and C. The start state is A. The accepting state is A. The transitions are:
When in state A, inputs 0, 3, 6 and 9 go to state A. Inputs 1, 4 and 7 go to state B. Inputs 2, 5 and 8 go to state C.
When in state B, inputs 0, 3, 6 and 9 go to state B. Inputs 1, 4 and 7 go to state C. Inputs 2, 5 and 8 go to state A.
When in state C, inputs 0, 3, 6 and 9 go to state C. Inputs 1, 4 and 7 go to state A. Inputs 2, 5 and 8 go to state B.
All other inputs go to an error state.
And we're done; we have a finite state machine that checks for divisibility by 3. Therefore we can build a regexp that checks for divisibility by 3; if we combine that with the regexp that checks for divisibility by 20, then we have the desired regular expression. The language of numbers written in decimal notation divisible by 60 is a regular language.
The actual construction of such a regular expression is left as an exercise. (Looks like that's what tiftik has done.)
Exercise: can you come up with a regular expression that determines if string contains a decimal number that is evenly divisible by 70? If you can, let's see it. If not, can you provide a proof that no such regular expression exists? (That is, that the language I am describing is not regular.)

I've come up with this:
^((?=[^147]*(([147][^147]*){3})*$)(?=[^258]*(([258][^258]*){3})*$)|(?=[^147]*(([147][^147]*){3})*[147][^147]*$)(?=[^258]*(([258][^258]*){3})*[258][^258]*$)|(?=[^147]*(([147][^147]*){3})*([147][^147]*){2}$)(?=[^258]*(([258][^258]*){3})*([258][^258]*){2}$))\d*0(?<=[02468][048]|[13579][26]|^0)$
Note: I didn't use non-capturing groups for the sake of simplicity.
Edit: Shorter version:
^(?=[^147]*(?:(?:[147][^147]*){3})*(?:()|([147][^147]*)|((?:[147][^147]*){2}))$)(?=[^258]*(?:(?:[258][^258]*){3})*(?:()|([258][^258]*)|((?:[258][^258]*){2}))$)((?(1)(?(4)|.$)|.$)|(?(2)(?(5)|.$)|.$)|(?(3)(?(6)|.$)|.$))\w*0(?<=[02468]0|^0)$

(+,/,-,*) in Regex are not used as mathematical operators. Use JavaScript instead.

Note: Regular expressions are not the right tool for this. This is just for fun and to see how it could be done.
Here is a regular expression that tests if a number is divisible by 60:
^0$|^(?!0)(?=.*[02468]0$)(?:[0369]|[147](?:[0369]*[147][0369]*[258])*(?:[0369]*[258]|[0369]*[147][0369]*[147])|[258](?:[0369]*[258][0369]*[147])*(?:[0369]*[147]|[0369]*[258][0369]*[258]))*0$
It works by testing if the number is divisible by 3 and using a lookahead to check if it is divisble by 20. It differs from the regular expression posted by tiftik in the following ways:
It is slightly shorter.
It uses non-capturing groups.
Many languages (for example Javascript )don't support variable length lookbehind assertions. This regular expression does not use lookbehinds so it can for example also be used for client-side validation in a web application.
It disallows numbers with leading zeros (if you want to allow leading zeros just remove the (?!0)).
This is the code I used to generate and test it:
using System;
using System.Text;
using System.Text.RegularExpressions;
class Program
{
Regex createRegex()
{
string a = "[0369]*";
string b = "a[147]";
string c = "a[258]";
string r = "^0$|^(?!0)(?=.*[02468]0$)(?:[0369]|[147](?:bc)*(?:c|bb)|[258](?:cb)*(?:b|cc))*0$";
r = r.Replace("b", b).Replace("c", c).Replace("a", a);
return new Regex(r);
}
bool isDivisibleBy3(string s)
{
int sumOfDigits = 0;
foreach (char c in s)
{
sumOfDigits += c - '0';
}
return sumOfDigits % 3 == 0;
}
bool isDivisibleBy20(string s)
{
return Regex.IsMatch(s, "^0$|[02468]0$");
}
bool isDivisibleBy60(string s)
{
return isDivisibleBy3(s) && isDivisibleBy20(s);
}
bool isValid(string s)
{
return Regex.IsMatch(s, "^0$|^[1-9][0-9]*$");
}
void Run()
{
Regex regex = createRegex();
Console.WriteLine(regex);
// Test on some random strings.
Random random = new Random();
for (int i = 0; i < 100000; ++i)
{
int length = random.Next(50);
StringBuilder sb = new StringBuilder();
for (int j = 0; j < length; ++j)
{
sb.Append(random.Next(10));
}
string s = sb.ToString();
bool isMatch = regex.IsMatch(s);
bool expected = isValid(s) && isDivisibleBy60(s);
if (isMatch != expected)
{
Console.WriteLine("Failed for " + s);
}
}
}
static void Main()
{
new Program().Run();
}
}

Regular expressions are the wrong tool for this job. Instead, try dividing by 60 and see if there is no remainder:
if (value % 60 == 0) {
// is divisible by 60
// ... do something ...
}

Related

Efficiency of & 1 over % 2 [duplicate]

What is the fastest way to find if a number is even or odd?
It is pretty well known that
static inline int is_odd_A(int x) { return x & 1; }
is more efficient than
static inline int is_odd_B(int x) { return x % 2; }
But with the optimizer on, will is_odd_B be no different from is_odd_A? No — with gcc-4.2 -O2, we get, (in ARM assembly):
_is_odd_A:
and r0, r0, #1
bx lr
_is_odd_B:
mov r3, r0, lsr #31
add r0, r0, r3
and r0, r0, #1
rsb r0, r3, r0
bx lr
We see that is_odd_B takes 3 more instructions than is_odd_A, the main reason is because
((-1) % 2) == -1
((-1) & 1) == 1
However, all the following versions will generate the same code as is_odd_A:
#include <stdbool.h>
static inline bool is_odd_D(int x) { return x % 2; } // note the bool
static inline int is_odd_E(int x) { return x % 2 != 0; } // note the !=
What does this mean? The optimizer is usually sophisticated enough that, for these simple stuff, the clearest code is enough to guarantee best efficiency.
Usual way to do it:
int number = ...;
if(number % 2) { odd }
else { even }
Alternative:
int number = ...;
if(number & 1) { odd }
else { even }
Tested on GCC 3.3.1 and 4.3.2, both have about the same speed (without compiler optimization) as both result in the and instruction (compiled on x86) - I know that using the div instruction for modulo would be much slower, thus I didn't test it at all.
if (x & 1) is true then it's odd, otherwise it's even.
bool is_odd = number & 1;
int i=5;
if ( i%2 == 0 )
{
// Even
} else {
// Odd
}
int is_odd(int n)
{
if (n == 0)
return 0;
else if (n == 1)
return 1;
else
return !is_odd(n - 1);
}
Oh wait, you said fastest way, not funniest. My bad ;)
Above function only works for positive numbers of course.
Check to see if the last bit is 1.
int is_odd(int num) {
return num & 1;
}
If it's an integer, probably by just checking the least significant bit. Zero would be counted as even though.
The portable way is to use the modulus operator %:
if (x % 2 == 0) // number is even
If you know that you're only ever going to run on two's complement architectures, you can use a bitwise and:
if (x & 0x01 == 0) // number is even
Using the modulus operator can result in slower code relative to the bitwise and; however, I'd stick with it unless all of the following are true:
You are failing to meet a hard performance requirement;
You are executing x % 2 a lot (say in a tight loop that's being executed thousands of times);
Profiling indicates that usage of the mod operator is the bottleneck;
Profiling also indicates that using the bitwise-and relieves the bottleneck and allows you to meet the performance requirement.
Your question is not completely specified. Regardless, the answer is dependent on your compiler and the architecture of your machine. For example, are you on a machine using one's complement or two's complement signed number representations?
I write my code to be correct first, clear second, concise third and fast last. Therefore, I would code this routine as follows:
/* returns 0 if odd, 1 if even */
/* can use bool in C99 */
int IsEven(int n) {
return n % 2 == 0;
}
This method is correct, it more clearly expresses the intent than testing the LSB, it's concise and, believe it or not, it is blazing fast. If and only if profiling told me that this method were a bottleneck in my application would I consider deviating from it.
Check the least significant bit:
if (number & 0x01) {
// It's odd
} else {
// It's even
}
Can't you just look at the last digit and check if its even or odd if the input is in base 10?
{1, 3, 5, 7, 9} is odd
{0, 2, 4, 6, 8} is even
Additional info: The OP states that a number is a given, so I went with that when constructing this answer. This also requires the number to be in base 10. This answer is mathematically correct by definition of even/odd in base 10. Depending on the use case, you have a mathematically consistent result just by checking the last digit.
Note: If your input is already an int, just check the low bit of that. This answer is only useful for numbers represented as a sequence of digits. You could convert int->string to do this, but that would be much slower than n % 2 == 0.
Checking the last digit does work for a string of digits in any even base, not just 10. For bases lower than 10, like base 8 (octal), 9 and 8 aren't possible digits, but the low digit being odd or even still determines whether the whole number is.
For bases higher than 10, there will be extra possibilities, but you don't want to search a list anyway, just check if the digit as an integer is odd or even using the normal i % 2 == 0 or !=0 check.
For ASCII hex using 'a' .. 'f' to represent digits values 10 through 15, the low bit of ASCII code does not represent odd or even, because 'a' == 0x61 (odd) but represents 10 aka 0xa (even). So you'd have to convert the hex digit to an integer, or do some bit-hack on the ASCII code to flip the low bit according to some other bit or condition.

Generate all numbers of length M (1<M<10) with elements from {1,2,...N} with N(1<N<20)

thank you for taking the time to read this.
I'm working on a larger project that needs a function that generates all numbers based on the rules described in the title.
If inputs are M=3 and N=5 Outputs should be: 111,112,113,114,115,121....555
For inputs M=4 and N=2 Outputs should be: 1111,1112,1121...2222
I've been trying to make a function that does this for quite some time but i haven't succeeded. So I'm asking for help. I'm required to write it in C, but if you know how to fix it in C++ or C# I'll probably be able to translate it into C.
I don't have any code to show because thus far I've mostly tried brute-forcing it but it doesn't seem to work
Thank you for the help in advance!
If I understand the question, I would do it with regular expressions. This is all written with C in mind.
First build a regex with all the allowed digits. Posix provides a regex library (https://www.educative.io/edpresso/how-to-write-regular-expressions-in-c appears to be a good intro), so you only have to compose the string that will be parsed by regcomp() by iterating through the numbers from 1 to N. An appropriate regular expression would be, for N=20, ^(1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20)+$. This will match strings composed entirely of any of those characters. (Since 0 should match only after 1 or 2 in this case, enumerating the options is simpler than trying to shorten the regex).
Then, iterate over the numbers starting with 10 ^ M and ending when you reach 10^(M+1). Write each number out as a string and see if it matches the regular expression - if it does, you have one of your results.
The problem can be boiled down to starting an M-digit, base-N number at its lowest value for the initial iteration, and incrementing it for subsequent iterations.
The M-digit number can be represented as an array (indexed from 0 to M-1) with one element per digit. One end of the array will hold the lowest order ("rightmost") digit and the other end of the array will hold the highest order ("leftmost") digit. It doesn't really matter which end is chosen to hold the highest order digit, so let's choose element 0 to hold the highest order digit. For generality, let's use digit values from 0 to N-1. (It doesn't really matter that the original problem has digits going from 1 to N since it is easy to map digit values from one scheme to the other.)
We can define a function to set the M-digit number to its lowest value:
void num_init(unsigned int *digits, unsigned int m)
{
while (m--)
{
digits[m] = 0;
}
}
We can define another function to increment the M-digit number and indicate whether the number has wrapped around back to its lowest value:
int num_inc(unsigned int *digits, unsigned int n, unsigned int m)
{
while (m--)
{
if (digits[m] < n - 1)
{
digits[m]++;
return 0;
}
digits[m] = 0; // carry
}
return 1;
}
Example usage:
// Print all M-digit numbers with digits from 1 to N.
void list_nums(unsigned int m, unsigned int n)
{
unsigned int digits[m];
int wrapped = 0;
num_init(digits, m);
while (!wrapped)
{
unsigned int i;
// output an m-digit number
for (i = 0; i < m; i++)
{
// Note: Add 1 to each digit so digits run from 1 to n instead of 0 to n-1.
printf("%u", digits[i] + 1);
}
// get next number
wrapped = num_inc(digits, n, m);
if (!wrapped)
{
printf(",");
}
}
printf("\n");
}
Note: The output of list_nums(m, n) will be strange when n is greater than 9.

C# - Constantly adding 9 digits

As the title says, I'm developing in C#.
I'd like to generate a number which has more than 9 numbers, so I thought about generating numbers, follow by 9.
For instance, if I want to generate a number which has 10 digits - I'd generate first a number which has 9 numbers, and then a number which has 1 digit.
If I generate the number 20, I'd generate first 2 numbers with 9 digits each, and then a number with 2 digits.
This is what I've tried:
for (int i = 0, j = (int.Parse(inputRandom.Text) % 9 == 0 ? int.Parse(inputRandom.Text) % 9 : int.Parse(inputRandom.Text) % 9 + 1); i < j; i++)
if (i < (int.Parse(inputRandom.Text) % 9 == 0 ? j % 9 : j % 9 + 1) - 1)
numToSend += (BigInteger)r.Next(int.Parse(1 + Zero((int.Parse(inputRandom.Text) % 9 + 8) * (inputRandom.Text.Length - 1))));
else
numToSend += (BigInteger)r.Next(int.Parse(1 + Zero(int.Parse(inputRandom.Text) % 9 * 9)));
The method Zero returns a string with 0, times the number specified in. I.e Zero(1) would return: "0"
I need this method because the method Next(Int32) can return a number, up to what specified between the brackets. I.e Next(10) would return a number between 0 and 9.
My goal
I want to generate a number with a number of digit above 9, and put the number into the string numToSend. I cannot simply do this, because the method Next() can only generate ints.
Even after your edit, I don't find the question very clear. However, I do think I understand that you are essentially trying to generate a random BigInteger value, and that you want the random value to be within a range defined by some specific number of digits.
For example, if you ask for a 10-digit value, some value between 0 and 9999999999 should be returned. If you ask for a 20-digit value, some value between 0 and 99999999999999999999 should be returned.
Based on that understanding, I believe this method should accomplish what you are asking:
BigInteger NextRandom(Random random, int digitCount)
{
BigInteger result = 0;
while (digitCount-- > 0)
{
result = result * 10 + random.Next(10);
}
return result;
}
Note that the number returned could have fewer than digitCount actual digits in it. In fact, there's always a 1-in-10 chance of that happening. And a 1-in-100 chance of the result having fewer than (digitCount - 1) digits, etc.
If you want something different from that, please be more specific about the exact requirements of the output you want (read https://stackoverflow.com/help/how-to-ask for advice on how to present your question in a clear, answerable way).
For example, the above won't generate a random value within some arbitrary range; the (exclusive) max value can only ever be a power of 10. Also, due to the way BigInteger works, if you are looking for a value with a specific number of binary digits, you can do that simply by using the Random.NextBytes() method, passing the resulting array (making modifications as appropriate to ensure e.g. positive values).
See also C# A random BigInt generator for more inspiration (I would've voted as that for a duplicate, but it seems from your description that you might be looking for a slightly different result than what's requested in that question).

Obsfucate a 5 digit number

I wish to obfuscate a 5 digit number
Properties of the obfuscated number that I care about:
it's impossible (or as a fall back, extremely unlikely) to collide with other obfuscated numbers
it's also a 5 digit number (no alpha characters please)
it's not easily determinable by a regular human without computational assistance (e.g. it's not something obvious like "multiply by 2 and subtract 5"
it's an algorithm ... as opposed to storing a look up table of all possible 5 digit numbers to their corresponding hash or some other "brute force" technique
Properties of the obfuscated number that I don't care about:
whether it's repeatable or not i.e. if "12345" always results in "73624", I okay
whether it's cryptographically secure or not
Thus far I haven't found anything that fits my requirements... but am hoping this is due to poor memory, incomplete education or dubious lifestyle choices rather than no "nice" solution being present.
An example that can be easily translated into C# would be a bonus.
Update:
I'm investigating using the idea of doing a simple bit mapping for the moment.
static List<int> bitMapping = new List<int>() { 8, 6, 9, 3, 7, 5, ... etc... };
private static int Obfuscate(int number)
{
var bits = new bool[bitMapping.Count];
foreach (var ordinal in bitMapping)
{
var mask = (int)Math.Pow(2, ordinal);
var bit = (mask & number) == mask;
var mappedOrdinal = bitMapping[ordinal];
bits[mappedOrdinal] = bit;
}
var obfuscatedNumber = 0;
for (var ordinal = 0; ordinal < bits.Length; ordinal++)
{
if (bits[ordinal])
{
obfuscatedNumber += (int)Math.Pow(2, ordinal);
}
}
return obfuscatedNumber;
It seems to meet most of my requirements thus far.
That might be too simple for your needs, but something that works and might not be as obvious as an addition is the XOR operation :
12345 ^ 65535 = 53190
53190 ^ 65535 = 12345
As noted in comments it is important that the second operand is of the form (2n - 1) to avoid collisions (so that every bit in the original number is inverted). It also needs to be long enough that its number of bits is greater or equal than the first operand.
You might also have to pad-left with 0's to make the result a 5-digit number.
If you don't want collisions then multiplication/division are out. In which case then I would
Add a 5 digit seed value to your number, if it overflows into six digits discard the sixth.
Reorder the digits in some consistent way.
E.g.
12345 + 97531 = 109876 or 09876 after discard overflow
Reorder to 68097

How to remove a number from another number using bitwise operators?

How do I remove for example 2 from 123 and returns 13, by using bitwise operators? I have no idea how to do this.. it's possible? Thanks in advance.
What you're suggesting is possible, but wouldn't really make sense to do. Below are the values representations in bits (only showing relevant bits, everything further left is a zero):
2: 000010 || 123: 1111011 || 13: 001101
There's no logical way to change 123 into 13 with bitwise operations. It would better to turn it into a string or character array, remove the two then cast it back to an int.
What other cases are there? It may be possible to generalize this at an integer level if there is some sort of pattern, otherwise you're really just looking at string replacement.
The 2 in 123 is actually 2E1 (10100), and the 2 in 1234 would be 2E2 (11001000) neither of which are related to 2 (10), at least in bitwise form. Also, the "number" on the right side of the removed number would need to be added to the number on the left side of the removed number / 10.
i.e, to go from 123 to 13:
Located "2".
Number on left (x): 100
Number on right (y): 3
y + (x / 10) = 13
and to go from 1324 to 134
Located "2"
Number on left (x): 1300
Number on right (y): 4
y + (x / 10) = 134
Unless there's some pattern (i.e you know what positions the numbers are in), you'll just have to .ToString() the number, then do a .Replace("2", ""), before doing an int.Parse() on the result.
EDIT: Someone upvoted this answer and I realised my previous implementation was unnecessarily complicated. It is relatively straightforward to 'iterate' over the digits in a base-10 number and shouldn't require recursion.
New solution below, performance is better but this is a huge micro-optimisation:
static int OmitDigit(int number, int digit) {
var output = 0;
var multiplier = 1;
while (number > 0) {
var n = number % 10;
number /= 10;
if (n != digit) {
output += (n * multiplier);
multiplier *= 10;
}
}
return output;
}
Result:
1554443
Since we're working with base 10 numbers, manipulation in base 2 is ugly to say the least. Using some math, removing the nth digit from k, and shifting over is
(k/pow(10,n))*pow(10, n-1) + k%pow(10, n-1)
In base 2, the << and >> operator acts like multiplying by a pow(2, n), and & with a mask does the work of %, but in base 10 the bits don't line up.
This is very awkward, but if you really do must have bitwise operations only, I suggest you convert the number to BCD. Once in BCD, you basically have an hexadecimal numbers with digits between 0 and 9, so removing a digit is very simple. Once you're done, convert back to binary.
I don't believe anybody would want to do that.

Categories

Resources