Newbie question: modulo operator with negative operand, bug or feature?


 
Thread Tools Search this Thread
Top Forums Shell Programming and Scripting Newbie question: modulo operator with negative operand, bug or feature?
# 1  
Old 08-11-2015
Newbie question: modulo operator with negative operand, bug or feature?

Hi,

I'm new to the Ash shell so my apologies if this is well known. In normal maths and other shells and languages I've used, the modulo operator always returns a positive remainder. For example see this discussion (first post so I can't hyperlink it):

http://math.stackexchange.com/questions/519845/modulo-of-a-negative-number

The Ash shell (and I am told Bash too) return a negative result. This code run on BusyBox illustrates the problem:

Code:
#!/bin/sh
echo "The result of A % B should be an integer in the range 0 to B-1"
echo "(9-7) % 5 = $(((9-7)%5)) (should be 2)."
echo "(7-9) % 5 = $(((7-9)%5)) (should be 3)."
exit 0

Is this accepted as just a 'feature' of the shells or is it a bug?
This User Gave Thanks to FleetFoot For This Post:
# 2  
Old 08-11-2015
Code:
echo "(9-7) % 5 = $(( $(( 9 - 7 )) % 5 )) (should be 2)."
# and
echo "(9-7) % 5 = $(( ( 9 - 7 ) % 5 )) (should be 2)."

Note the spaces.

Both work in bash. /bin/sh does not have to always equal bash, it should a modern POSIX shell. I do not know how /bin/sh evaluates on busybox.
# 3  
Old 08-11-2015
I tried every shell I could find and the answer was:
Code:
$ dash modtest
The result of A % B should be an integer in the range 0 to B-1
(9-7) % 5 = 2 (should be 2).
(7-9) % 5 = -2 (should be 3).

across all POSIX shells, dash (Debian Almquist Shell), bash, ksh88, ksh93, zsh...
# 4  
Old 08-11-2015
Code:
aia@localhost fleefoot]$ echo "(7-9) % 5 = $(((7-9)%5)) (should be 3)."
(7-9) % 5 = -2 (should be 3).

-2%5 is -2 according how the sign is handled in languages that satisfy it as a = ((a / b) * b) + (a % b)


An example to show the difference using Perl
Code:
[aia@localhost fleefoot]$ perl -le 'print -2%5'
3
[aia@localhost fleefoot]$ perl -le 'print (-2)%5'
-2


Last edited by Aia; 08-11-2015 at 02:51 PM..
# 5  
Old 08-11-2015
Hi.

Quote:
In computing, the modulo operation finds the remainder after division of one number by another (sometimes called modulus).

Given two positive numbers, a (the dividend) and n (the divisor), a modulo n (abbreviated as a mod n) is the remainder of the Euclidean division of a by n.
..
When either a or n is negative, the naive definition breaks down and programming languages differ in how these values are defined.
-- https://en.wikipedia.org/wiki/Modulo_operation

Best wishes ... cheers, drl
These 2 Users Gave Thanks to drl For This Post:
# 6  
Old 08-11-2015
@Scrutinizer - what did you try, the original code? The '$((' '))' construct requires spaces around it I believe.

NO! it does not need spaces, just leading spaces

I'm wrong - the $(( does not require spaces it is part of command substitution (from opnegroup.org):
Quote:
If the current character is an unquoted '$' or '`', the shell shall identify the start of any candidates for parameter expansion ( Parameter Expansion), command substitution ( Command Substitution), or arithmetic expansion ( Arithmetic Expansion) from their introductory unquoted character sequences: '$' or "${", "$(" or '`', and "$((", respectively.
But since that is true then why do we get wacky (divergent) results with POSIX-compliant shells? my ksh did not like it. My bash (3.4.3) did after I added some spaces. It specifically complained about %5. Hmm.
# 7  
Old 08-11-2015
Quote:
Originally Posted by Aia
[...]

-2%5 is -2 according how the sign is handled in languages that satisfy it as a = ((a / b) * b) + (a % b)


An example to show the difference using Perl
Code:
[aia@localhost fleefoot]$ perl -le 'print -2%5'
3
[aia@localhost fleefoot]$ perl -le 'print (-2)%5'
-2

Aia, could you elaborate on why that should render a different outcome ?

In awk:
Code:
awk 'BEGIN {print (-2)%5, -2%5}'
-2 -2

Quote:
Originally Posted by jim mcnamara
@Scrutinizer - what did you try, the original code? [..]
Hi Jim, yes, the original code...
Quote:

NO! it does not need spaces, just leading spaces

I'm wrong - the $(( does not require spaces it is part of command substitution (from opnegroup.org):


But since that is true then why do we get wacky (divergent) results with POSIX-compliant shells? my ksh did not like it. My bash (3.4.3) did after I added some spaces. It specifically complained about %5. Hmm.
What ksh and bash are those on what OS? Any ksh I tried and any bash on any OS did not seem to have a problem with it,

Last edited by Scrutinizer; 08-11-2015 at 01:45 PM..
Login or Register to Ask a Question

Previous Thread | Next Thread

8 More Discussions You Might Find Interesting

1. What is on Your Mind?

Bug Reporting and Feature Request Tracking on GitHub

Dear All, I created a "new public repo" on GitHub (without the code for now but will post the code there as needed if anyone wants to fix a bug) You can report any forum bugs and report issues in the GitHub "Issues Tab" for this repo here: https://github.com/unixneo/unix.com.bugtracker ... (0 Replies)
Discussion started by: Neo
0 Replies

2. Shell Programming and Scripting

Assignment operator without operand

Does anyone know how this line in bash works? local gotbase= force= nicelevel corelimit local pid base= user= nice= bg= pid_file= local cgroup= These lines are part of the daemon function inside the "functions" file at /etc/init.d in RH. (3 Replies)
Discussion started by: Rameshck
3 Replies

3. Shell Programming and Scripting

Modulo calculation in shell script

hi i am writing a progrm to print the even numbers and the code which i am following is as follows #!/usr/bin/bash echo "enter a number a" read a if then echo "the number is even" else echo "the number is odd" fi ~ what is the mistake i am doing ...please tell me (3 Replies)
Discussion started by: harjinder
3 Replies

4. Shell Programming and Scripting

OR operator syntax question in AWK script

Hi guys, I confused about syntax used in OR script as follow: I have this sample file separated by "|" containing: January|Month No. 1 February|Month No. 2 March|Month No. 3 April|Month No. 4 May|Month No. 5 June|Month No. 6 July|Month No. 7 August|Month No. 8 September|Month No. 9... (11 Replies)
Discussion started by: cgkmal
11 Replies

5. Shell Programming and Scripting

perl newbie . &&..programming newbie (question 2)

Hello everyone, I am having to do a lot of perl scripting these days and I am learning a lot. I have this problem I want to move files from a folder and all its sub folders to one parent folder, they are all .gz files.. there is folder1\folder2\*.gz and there are about 50 folders... (1 Reply)
Discussion started by: xytiz
1 Replies

6. UNIX for Dummies Questions & Answers

UNIX newbie NEWBIE question!

Hello everyone, Just started UNIX today! In our school we use solaris. I just want to know how do I setup Solaris 10 not the GUI one, the one where you have to type the commands like ECHO, ls, pwd, etc... I have windows xp and I also have vmware. I hope I am not missing anything! :p (4 Replies)
Discussion started by: Hanamachi
4 Replies

7. Shell Programming and Scripting

syntax error: `-a' unexpected operator/operand in IF

When i tyr this, it gives me a syntax error...i tried removing quotes,removing spaces,replacing -eq with '='.. Can somebody suggest that is the problem? if ]; then (4 Replies)
Discussion started by: dba.admin2008
4 Replies

8. UNIX for Dummies Questions & Answers

Operator question

I need to find out if a variable contains a certain text string, then do something about it. Here is what I mean, but I don't know how to get a "contains" operator # We have volumes called: # /Volumes/BackupsA_K # /Volumes/BackupsL_Z # /Volumes/Backups_Admin # (could be more, etc)... (5 Replies)
Discussion started by: TheCrunge
5 Replies
Login or Register to Ask a Question