How would I go about making a function so that x has a range of values from x=0 to x=19 and if the x value exceeds 19 or is below zero how can I get it to wrap around
From:
x=20, x=21, x=22 and x=(-1), x=(-2), x=(-3)
To:
x=0, x=1, x=2 and x=19, x=18, x=17 respectively?
I've heard of modular arithmetic which is apparently the way I should deal with it.
Usually you would use the built-in functions mod and rem, but I assume they are off-limits for homework. So you can write your own function, e.g.
mod20 x | x < 0 = ...
| x > 19 = ...
| otherwise = x
There are different things you can try to fill in the ...s. One of the easiest is repeated addition or subtraction, but I don't want to spoil all the fun.
Once you have this function, you can "rescale" the values after every "normal" arithmetic operation, e.g. mod20 (12 + 17).
Try using the mod function:
(-5) `mod` 20 ==> 15
5 `mod` 20 ==> 5
20 `mod` 20 ==> 0
25 `mod` 20 ==> 5
See also wikipedia on the topic.
Use
x `mod` 20
(This is a filler to make the answer 30 characters.)
Related
I have data in Stata regarding the feeling of the current situation. There are seven types of feeling. The data is stored in the following format (note that the data type is a string, and one person can respond to more than 1 answer)
feeling
4,7
1,3,4
2,5,6,7
1,2,3,4,5,6,7
Since the data is a string, I tried to separate it by
split feeling, parse (,)
and I got the result
feeling1
feeling2
feeling3
feeling4
feeling5
feeling6
feeling7
4
7
1
3
4
2
5
6
7
1
2
3
4
5
6
7
However, this is not the result I want. which is that the representative number of feelings should go into the correct variable. For instance.
feeling1
feeling2
feeling3
feeling4
feeling5
feeling6
feeling7
4
7
1
3
4
2
5
6
7
1
2
3
4
5
6
7
I am not sure if there is any built-in command or function for this kind of problem. I am thinking about using forval in looping through every value in each variable and try to juggle it around into the correct variable.
A loop over the distinct values would be enough here. I give your example in a form explained in the Stata tag wiki as more helpful and then give code to get the variables you want as numeric variables.
* Example generated by -dataex-. For more info, type help dataex
clear
input str13 feeling
"4,7"
"1,3,4"
"2,5,6,7"
"1,2,3,4,5,6,7"
end
forval j = 1/7 {
gen wanted`j' = `j' if strpos(feeling, "`j'")
gen better`j' = strpos(feeling, "`j'") > 0
}
l feeling wanted1-better3
+---------------------------------------------------------------------------+
| feeling wanted1 better1 wanted2 better2 wanted3 better3 |
|---------------------------------------------------------------------------|
1. | 4,7 . 0 . 0 . 0 |
2. | 1,3,4 1 1 . 0 3 1 |
3. | 2,5,6,7 . 0 2 1 . 0 |
4. | 1,2,3,4,5,6,7 1 1 2 1 3 1 |
+---------------------------------------------------------------------------+
If you wanted a string result that would be yielded by
gen wanted`j' = "`j'" if strpos(feeling, "`j'")
Had the number of feelings been 10 or more you would have needed more careful code as for example a search for "1" would find it within "10".
Indicator (some say dummy) variables with distinct values 1 or 0 are immensely more valuable for most analysis of this kind of data.
Note Stata-related sources such as
this FAQ
this paper
and this paper.
170! approaches the limit of a floating point double: 171! will overflow.
However 170! is over 300 digits long.
There is, therefore, no way that 170! can be represented precisely in floating point.
Yet Excel returns the correct answer for 170! / 169!.
Why is this? I'd expect some error to creep in, but it returns an integral value. Does Excel somehow know how to optimise this calculation?
If you find the closest doubles to 170! and 169!, they are
double oneseventy = 5818033100654137.0 * 256;
double onesixtynine = 8761273375102700.0;
times the same power of two. The closest double to the quotient of these is exactly 170.0.
Also, Excel may compute 170! by multiplying 169! by 170.
William Kahan has a paper called "How Futile are Mindless Assessments of Roundoff in Floating-Point Computation?" where he discusses some of the insanity that goes on in Excel. It may be that Excel is not computing 170 exactly, but rather it's hiding an ulp of reality from you.
The answer of tmyklebu is already perfect. But I wanted to know more.
What if implementation of n! was something trivial as return double(n)*(n-1)!...
Here is a Smalltalk snippet, but you can translate in many other languages, that's not the point:
(2 to: 170) count: [:n |
| num den |
den := (2 to: n - 1) inject: 1.0 into: [:p :e | p*e].
num := n*den.
num / den ~= n].
And the answer is 12
So you have not been particulary lucky, due to good properties of round to nearest even rounding mode, out of these 169 numbers, only 12 don't behave as expected.
Which ones? Replace count: by select: and you get:
#(24 47 59 61 81 96 101 104 105 114 122 146)
If I had an Excel handy, I would ask to evaluate 146!/145!.
Curiously (only apparently curiously), a less naive solution that computes the exact factorial with large integer arithmetic, then convert to nearest float, does not perform better !
(2 to: 170) reject: [:n |
n factorial asFloat / (n-1) factorial asFloat = n]
leads to:
#(24 31 34 40 41 45 46 57 61 70 75 78 79 86 88 92 93 111 115 116 117 119 122 124 141 144 147 164)
So I've been working on this problem of printing out a Sudoku board for the past couple hours and I'm almost finished but I'm stuck at the final step. So what I have is a Sudoku board represented as a "list of lists" (i.e. board = [[1, 3, 5, 7, 0, 2, 0, 0, 0], [3, 4, 5, ...], ...]
I've been able to print out a line with formatting with the following function:
line i s_board = intercalate " | " . map unwords . chunksOf 3 $ map show a
where
a = s_board!!i
So by making a call like "line 0 board" i would get "1 3 5 | 7 0 2 | 0 0 0" which is partially what I need. Next I tried to use a "do block" to output the board that I need which looked something like this:
print = do line 0 board
line 1 board
...
This wouldn't even compile, and when I did something like this:
print = do
line 0 board
line 1 board
The appropriate list was printed multiple times which is fairly confusing. I wanted to work my way up to including extra formatting such as printing a string such as "----------" after every three lines to complete the board but I can't even get the other thing to work right yet. I'd appreciate any help offered with these issues.
It would be easier and more elegant to produce a function that takes your
board, makes one big string, and finally prints it, rather than worrying about
printing every line via a do block.
So, if we simplify your line showing function to take one line of the board:
showLine :: [Int] -> String
showLine = intercalate " | "
. map unwords
. chunksOf 3
. map show
Then, we need to get the string representation of each line and put them all
together. This looks pretty much like the showLine code:
showBoard :: [[Int]] -> String
showBoard = intercalate "---------------------\n"
. map unlines
. chunksOf 3
. map showLine
Using the example board
-- Obviously not a valid sudoku board...
example :: [[Int]]
example = replicate 9 [ 1, 2, 3, 4, 5, 6, 7, 8, 9 ]
*Main> putStrLn $ showBoard example
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
---------------------
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
---------------------
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
1 2 3 | 4 5 6 | 7 8 9
Your original attempt didn't compile because it violates Haskell's layout rules.
The second didn't do what you expect because line n board is a list, so the do-notation means nondeterminism, not sequencing of IO actions. If you tried to put a type like
print :: IO ()
above your function (incidentally, print is defined in the Standard Prelude and you should be getting a warning about shadowing it), the type-checker would inform you of your mistake. If you really wanted to print out the board like this (although as the other answer suggests, building a string and then printing this whole thing out is much better), you could try
printBoard :: IO ()
printBoard = do print $ line 0 board
print $ line 1 board
or to print the whole board,
printBoard = mapM_ (print . showLine) board
where showLine is like your print but with the indexing stripped out.
Since length is a generic method, why can't I do
length.character <- nchar
? It seems that strings are treated special in R. Is there a reason for that? Would you discourage defining functions like head.character and tail.character?
If you look at the help page for InternalMethods (mentioned in the details portion of the help page for length) it states that
For efficiency, internal dispatch only
occurs on objects, that
is those for which ‘is.object’ returns true.
Vectors are not objects in the same sense as other objects are, so the method dispatch is not being done on any basic vectors (not just character). if you really want to use this type of dispatch you need a defined object, e.g.:
> tmp <- state.name
> class(tmp) <- 'mynewclass'
> length.mynewclass <- nchar
> length(tmp)
[1] 7 6 7 8 10 8 11 8 7 7 6 5 8 7 4 6 8 9 5 8 13 8 9 11 8
[26] 7 8 6 13 10 10 8 14 12 4 8 6 12 12 14 12 9 5 4 7 8 10 13 9 7
>
My 2c:
Strings are not treated specially in R. If length did the same thing as nchar, then you would get unexpected results if you tried to compute length(c("foo", "bazz")). Or to put it another way, would you expect the length of a numeric vector to return the number of digits in each element of the vector or the length of the vector itself?
Also creating this method might side-effect other functions which expect the normal string behavior.
Now I found a reason not to define head.character: it changes the way how head works. For example:
head.character <- function(s,n) if(n<0) substr(s,1,nchar(s)+n) else substr(s,1,n)
test <- c("abc", "bcd", "cde")
head("abc", 2) # works fine
head(test,2)
Without the definition of head, the last line would return c("abc", "bcd"). Now, with head.character defined, this function is applied to each element of the list and returns c("ab", "bc", "cd").
But I have a strhead and a strtail function now.. :-)
How would I round the result from two divided numbers, e.g.
3/2
As when I do
testOne=$((3/2))
$testOne contains "1" when it should have rounded up to "2" as the answer from 3/2=1.5
To do rounding up in truncating arithmetic, simply add (denom-1) to the numerator.
Example, rounding down:
N/2
M/5
K/16
Example, rounding up:
(N+1)/2
(M+4)/5
(K+15)/16
To do round-to-nearest, add (denom/2) to the numerator (halves will round up):
(N+1)/2
(M+2)/5
(K+8)/16
Good Solution is to get Nearest Round Number is
var=2.5
echo $var | awk '{print int($1+0.5)}'
Logic is simple if the var decimal value is less then .5 then closest value taken is integer value. Well if decimal value is more than .5 then next integer value gets added and since awk then takes only integer part. Issue solved
bash will not give you correct result of 3/2 since it doesn't do floating pt maths. you can use tools like awk
$ awk 'BEGIN { rounded = sprintf("%.0f", 3/2); print rounded }'
2
or bc
$ printf "%.0f" $(echo "scale=2;3/2" | bc)
2
If you have integer division of positive numbers which rounds toward zero, then you can add one less than the divisor to the dividend to make it round up.
That is to say, replace X / Y with (X + Y - 1) / Y.
Proof:
Case 1: X = k * Y (X is integer multiple of Y): In this case, we have (k * Y + Y - 1) / Y, which splits into (k * Y) / Y + (Y - 1) / Y. The (Y - 1)/Y part rounds to zero, and we are left with a quotient of k. This is exactly what we want: when the inputs are divisible, we want the adjusted calculation to still produce the correct exact quotient.
Case 2: X = k * Y + m where 0 < m < Y (X is not a multiple of Y). In this case we have a numerator of k * Y + m + Y - 1, or k * Y + Y + m - 1, and we can write the division out as (k * Y)/Y + Y/Y + (m - 1)/Y. Since 0 < m < Y, 0 <= m - 1 < Y - 1, and so the last term (m - 1)/Y goes to zero. We are left with (k * Y)/Y + Y/Y which work out to k + 1. This shows that the behavior rounds up. If we have an X which is a k multiple of Y, if we add just 1 to it, the division rounds up to k + 1.
But this rounding is extremely opposite; all inexact divisions go away from zero. How about something in between?
That can be achieved by "priming" the numerator with Y/2. Instead of X/Y, calculate (X+Y/2)/Y. Instead of proof, let's go empirical on this one:
$ round()
> {
> echo $((($1 + $2/2) / $2))
> }
$ round 4 10
0
$ round 5 10
1
$ round 6 10
1
$ round 9 10
1
$ round 10 10
1
$ round 14 10
1
$ round 15 10
2
Whenever the divisor is an even, positive number, if the numerator is congruent to half that number, it rounds up, and rounds down if it is one less than that.
For instance, round 6 12 goes to 1, as do all values which are equal to 6, modulo 12, like 18 (which goes to 2) and so on. round 5 12 goes down to 0.
For odd numbers, the behavior is correct. None of the exact rational numbers are midway between two consecutive multiples. For instance, with a denominator of 11 we have 5/11 < 5.5/11 (exact middle) < 6/11; and round 5 11 rounds down, whereas round 6 11 rounds up.
Given a floating point value, we can round it trivially with printf:
# round $1 to $2 decimal places
round() {
printf "%.${2:-0}f" "$1"
}
Then,
# do some math, bc style
math() {
echo "$*" | bc -l
}
$ echo "Pi, to five decimal places, is $(round $(math "4*a(1)") 5)"
Pi, to five decimal places, is 3.14159
Or, to use the original request:
$ echo "3/2, rounded to the nearest integer, is $(round $(math "3/2") 0)"
3/2, rounded to the nearest integer, is 2
To round up you can use modulus.
The second part of the equation will add to True if there's a remainder. (True = 1; False = 0)
ex: 3/2
answer=$(((3 / 2) + (3 % 2 > 0)))
echo $answer
2
ex: 100 / 2
answer=$(((100 / 2) + (100 % 2 > 0)))
echo $answer
50
ex: 100 / 3
answer=$(((100 / 3) + (100 % 3 > 0)))
echo $answer
34
If the decimal separator is comma (eg : LC_NUMERIC=fr_FR.UTF-8, see here):
$ printf "%.0f" $(echo "scale=2;3/2" | bc)
bash: printf: 1.50: nombre non valable
0
Substitution is needed for ghostdog74 solution :
$ printf "%.0f" $(echo "scale=2;3/2" | bc | sed 's/[.]/,/')
2
or
$ printf "%.0f" $(echo "scale=2;3/2" | bc | tr '.' ',')
2
Another solution is to do the division within a python command. For example:
$ numerator=90
$ denominator=7
$ python -c "print (round(${numerator}.0 / ${denominator}.0))"
Seems less archaic to me than using awk.
I think this should be enough.
$ echo "3/2" | bc
Following worked for me.
#!/bin/bash
function float() {
bc << EOF
num = $1;
base = num / 1;
if (((num - base) * 10) > 1 )
base += 1;
print base;
EOF
echo ""
}
float 3.2