Initial upload
This commit is contained in:
37
go/luhn/.exercism/config.json
Normal file
37
go/luhn/.exercism/config.json
Normal file
@@ -0,0 +1,37 @@
|
||||
{
|
||||
"blurb": "Given a number determine whether or not it is valid per the Luhn formula.",
|
||||
"authors": [
|
||||
"soniakeys"
|
||||
],
|
||||
"contributors": [
|
||||
"alebaffa",
|
||||
"bitfield",
|
||||
"da-edra",
|
||||
"ekingery",
|
||||
"ferhatelmas",
|
||||
"hilary",
|
||||
"kytrinyx",
|
||||
"leenipper",
|
||||
"michaelorr",
|
||||
"petertseng",
|
||||
"robphoenix",
|
||||
"sebito91",
|
||||
"tehsphinx"
|
||||
],
|
||||
"files": {
|
||||
"solution": [
|
||||
"luhn.go"
|
||||
],
|
||||
"test": [
|
||||
"luhn_test.go"
|
||||
],
|
||||
"example": [
|
||||
".meta/example.go"
|
||||
],
|
||||
"editor": [
|
||||
"cases_test.go"
|
||||
]
|
||||
},
|
||||
"source": "The Luhn Algorithm on Wikipedia",
|
||||
"source_url": "http://en.wikipedia.org/wiki/Luhn_algorithm"
|
||||
}
|
1
go/luhn/.exercism/metadata.json
Normal file
1
go/luhn/.exercism/metadata.json
Normal file
@@ -0,0 +1 @@
|
||||
{"track":"go","exercise":"luhn","id":"848a867390e5471ab5f927ba5dad86a7","url":"https://exercism.org/tracks/go/exercises/luhn","handle":"halfdan","is_requester":true,"auto_approve":false}
|
2
go/luhn/.tool-versions
Normal file
2
go/luhn/.tool-versions
Normal file
@@ -0,0 +1,2 @@
|
||||
golang 1.17.2
|
||||
kubectx 0.9.3
|
40
go/luhn/HELP.md
Normal file
40
go/luhn/HELP.md
Normal file
@@ -0,0 +1,40 @@
|
||||
# Help
|
||||
|
||||
## Running the tests
|
||||
|
||||
To run the tests run the command `go test` from within the exercise directory.
|
||||
|
||||
If the test suite contains benchmarks, you can run these with the `--bench` and `--benchmem`
|
||||
flags:
|
||||
|
||||
go test -v --bench . --benchmem
|
||||
|
||||
Keep in mind that each reviewer will run benchmarks on a different machine, with
|
||||
different specs, so the results from these benchmark tests may vary.
|
||||
|
||||
## Submitting your solution
|
||||
|
||||
You can submit your solution using the `exercism submit luhn.go` command.
|
||||
This command will upload your solution to the Exercism website and print the solution page's URL.
|
||||
|
||||
It's possible to submit an incomplete solution which allows you to:
|
||||
|
||||
- See how others have completed the exercise
|
||||
- Request help from a mentor
|
||||
|
||||
## Need to get help?
|
||||
|
||||
If you'd like help solving the exercise, check the following pages:
|
||||
|
||||
- The [Go track's documentation](https://exercism.org/docs/tracks/go)
|
||||
- [Exercism's support channel on gitter](https://gitter.im/exercism/support)
|
||||
- The [Frequently Asked Questions](https://exercism.org/docs/using/faqs)
|
||||
|
||||
Should those resources not suffice, you could submit your (incomplete) solution to request mentoring.
|
||||
|
||||
To get help if you're having trouble, you can use one of the following resources:
|
||||
|
||||
- [How to Write Go Code](https://golang.org/doc/code.html)
|
||||
- [Effective Go](https://golang.org/doc/effective_go.html)
|
||||
- [Go Resources](http://golang.org/help)
|
||||
- [StackOverflow](http://stackoverflow.com/questions/tagged/go)
|
95
go/luhn/README.md
Normal file
95
go/luhn/README.md
Normal file
@@ -0,0 +1,95 @@
|
||||
# Luhn
|
||||
|
||||
Welcome to Luhn on Exercism's Go Track.
|
||||
If you need help running the tests or submitting your code, check out `HELP.md`.
|
||||
|
||||
## Instructions
|
||||
|
||||
Given a number determine whether or not it is valid per the Luhn formula.
|
||||
|
||||
The [Luhn algorithm](https://en.wikipedia.org/wiki/Luhn_algorithm) is
|
||||
a simple checksum formula used to validate a variety of identification
|
||||
numbers, such as credit card numbers and Canadian Social Insurance
|
||||
Numbers.
|
||||
|
||||
The task is to check if a given string is valid.
|
||||
|
||||
## Validating a Number
|
||||
|
||||
Strings of length 1 or less are not valid. Spaces are allowed in the input,
|
||||
but they should be stripped before checking. All other non-digit characters
|
||||
are disallowed.
|
||||
|
||||
### Example 1: valid credit card number
|
||||
|
||||
```text
|
||||
4539 3195 0343 6467
|
||||
```
|
||||
|
||||
The first step of the Luhn algorithm is to double every second digit,
|
||||
starting from the right. We will be doubling
|
||||
|
||||
```text
|
||||
4_3_ 3_9_ 0_4_ 6_6_
|
||||
```
|
||||
|
||||
If doubling the number results in a number greater than 9 then subtract 9
|
||||
from the product. The results of our doubling:
|
||||
|
||||
```text
|
||||
8569 6195 0383 3437
|
||||
```
|
||||
|
||||
Then sum all of the digits:
|
||||
|
||||
```text
|
||||
8+5+6+9+6+1+9+5+0+3+8+3+3+4+3+7 = 80
|
||||
```
|
||||
|
||||
If the sum is evenly divisible by 10, then the number is valid. This number is valid!
|
||||
|
||||
### Example 2: invalid credit card number
|
||||
|
||||
```text
|
||||
8273 1232 7352 0569
|
||||
```
|
||||
|
||||
Double the second digits, starting from the right
|
||||
|
||||
```text
|
||||
7253 2262 5312 0539
|
||||
```
|
||||
|
||||
Sum the digits
|
||||
|
||||
```text
|
||||
7+2+5+3+2+2+6+2+5+3+1+2+0+5+3+9 = 57
|
||||
```
|
||||
|
||||
57 is not evenly divisible by 10, so this number is not valid.
|
||||
|
||||
## Source
|
||||
|
||||
### Created by
|
||||
|
||||
- @soniakeys
|
||||
|
||||
### Contributed to by
|
||||
|
||||
- @alebaffa
|
||||
- @bitfield
|
||||
- @da-edra
|
||||
- @ekingery
|
||||
- @ferhatelmas
|
||||
- @hilary
|
||||
- @kytrinyx
|
||||
- @leenipper
|
||||
- @michaelorr
|
||||
- @petertseng
|
||||
- @robphoenix
|
||||
- @sebito91
|
||||
- @tehsphinx
|
||||
|
||||
### Based on
|
||||
|
||||
The Luhn Algorithm on Wikipedia - http://en.wikipedia.org/wiki/Luhn_algorithm
|
102
go/luhn/cases_test.go
Normal file
102
go/luhn/cases_test.go
Normal file
@@ -0,0 +1,102 @@
|
||||
package luhn
|
||||
|
||||
// Source: exercism/problem-specifications
|
||||
// Commit: f375a46 luhn: Update non-ASCII test case
|
||||
// Problem Specifications Version: 1.6.1
|
||||
|
||||
var testCases = []struct {
|
||||
description string
|
||||
input string
|
||||
ok bool
|
||||
}{
|
||||
{
|
||||
"single digit strings can not be valid",
|
||||
"1",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"a single zero is invalid",
|
||||
"0",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"a simple valid SIN that remains valid if reversed",
|
||||
"059",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"a simple valid SIN that becomes invalid if reversed",
|
||||
"59",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"a valid Canadian SIN",
|
||||
"055 444 285",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"invalid Canadian SIN",
|
||||
"055 444 286",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"invalid credit card",
|
||||
"8273 1232 7352 0569",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"valid number with an even number of digits",
|
||||
"095 245 88",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"valid number with an odd number of spaces",
|
||||
"234 567 891 234",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"valid strings with a non-digit added at the end become invalid",
|
||||
"059a",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"valid strings with punctuation included become invalid",
|
||||
"055-444-285",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"valid strings with symbols included become invalid",
|
||||
"055# 444$ 285",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"single zero with space is invalid",
|
||||
" 0",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"more than a single zero is valid",
|
||||
"0000 0",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"input digit 9 is correctly converted to output digit 9",
|
||||
"091",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"valid number with an odd number of digits and non-zero first digit",
|
||||
"109",
|
||||
true,
|
||||
},
|
||||
{
|
||||
"using ascii value for non-doubled non-digit isn't allowed",
|
||||
"055b 444 285",
|
||||
false,
|
||||
},
|
||||
{
|
||||
"using ascii value for doubled non-digit isn't allowed",
|
||||
":9",
|
||||
false,
|
||||
},
|
||||
}
|
3
go/luhn/go.mod
Normal file
3
go/luhn/go.mod
Normal file
@@ -0,0 +1,3 @@
|
||||
module luhn
|
||||
|
||||
go 1.13
|
33
go/luhn/luhn.go
Normal file
33
go/luhn/luhn.go
Normal file
@@ -0,0 +1,33 @@
|
||||
package luhn
|
||||
|
||||
import (
|
||||
"unicode"
|
||||
"strings"
|
||||
)
|
||||
|
||||
|
||||
// Valid checks a given number for validity according to Luhn's formula
|
||||
func Valid(card string) bool {
|
||||
sum := 0
|
||||
card = strings.ReplaceAll(card, " ", "")
|
||||
if len(card) <= 1 {
|
||||
return false
|
||||
}
|
||||
for idx, char := range card {
|
||||
if !unicode.IsDigit(char) {
|
||||
return false
|
||||
}
|
||||
digit := int(char - '0')
|
||||
if (len(card)-idx-1)%2 == 0 {
|
||||
sum += digit
|
||||
} else {
|
||||
digit *= 2
|
||||
if digit > 9 {
|
||||
sum += digit - 9
|
||||
} else {
|
||||
sum += digit
|
||||
}
|
||||
}
|
||||
}
|
||||
return sum%10 == 0
|
||||
}
|
20
go/luhn/luhn_test.go
Normal file
20
go/luhn/luhn_test.go
Normal file
@@ -0,0 +1,20 @@
|
||||
package luhn
|
||||
|
||||
import "testing"
|
||||
|
||||
func TestValid(t *testing.T) {
|
||||
for _, test := range testCases {
|
||||
if ok := Valid(test.input); ok != test.ok {
|
||||
t.Fatalf("Valid(%s): %s\n\t Expected: %t\n\t Got: %t", test.input, test.description, test.ok, ok)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func BenchmarkValid(b *testing.B) {
|
||||
if testing.Short() {
|
||||
b.Skip("skipping benchmark in short mode.")
|
||||
}
|
||||
for i := 0; i < b.N; i++ {
|
||||
Valid("2323 2005 7766 3554")
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user