42
\$\begingroup\$

Title stolen inspired by Greg Hewgill's answer to What's the difference between JavaScript and Java?

Introduction

Java and JavaScript are commonly used languages among programmers, and are currently the most popular tags on Stack Overflow. Yet aside from similar names, the two have almost nothing in common.

In honor of one of programming's most infamous debates, and inspired by my recent frustrations in tag searching, I propose the following:

Challenge

Write a program which takes in a string as input. Return car if the string begins with "Java" and does not include "JavaScript". Otherwise, return carpet.

Example Input and Output

car:

java
javafx
javabeans
java-stream
java-script
java-8
java.util.scanner
java-avascript
JAVA-SCRIPTING
javacarpet

carpet:

javascript
javascript-events
facebook-javascript-sdk
javajavascript
jquery
python
rx-java
java-api-for-javascript
not-java
JAVASCRIPTING

Notes

  • Input matching should be case insensitive
  • Only possibilities for output should be car or carpet
  • Imaginary bonus points if your answer uses Java, JavaScript, or Regex
  • Alternate Title: Java is to JavaScript as ham is to hamster
\$\endgroup\$
4
  • 2
    \$\begingroup\$ The new pattern-matching tag needs a wiki. Please contribute if you can \$\endgroup\$
    – user63187
    Jul 13, 2017 at 16:29
  • 2
    \$\begingroup\$ Depending on the order things are done in, javacarpet might catch bugs that the existing test cases don't. \$\endgroup\$
    – Ray
    Jul 13, 2017 at 21:17
  • 19
    \$\begingroup\$ If you get imaginary bonus points if your answer uses Java, Javascript, or Regex, does that make such solution's bytecount complex? ;) \$\endgroup\$
    – Steadybox
    Jul 13, 2017 at 21:34
  • 2
    \$\begingroup\$ Alternate Title: Java is to JavaScript as ham is to hamster Actually, the "ham" in "hamster" is cognate to the food "ham". The food "ham" is pig meat, and the term "hamster" is derived from the related animal, the guinea pig, whose meat replaced pigs meat on long sea voyages as the animals were easier to raise on a ship. \$\endgroup\$
    – dotancohen
    Jul 17, 2017 at 8:14

33 Answers 33

109
\$\begingroup\$

Java/JavaScript Polyglot, 108 107 106 bytes

//\u000As->s.matches("(?i)(?!.*javascript)java.*"/*
a=>/(?!.*javascript)^java/i.test(a/**/)?"car":"carpet"

Run as Java

//\u000As->s.matches("(?i)(?!.*javascript)java.*"/*
a=>/(?!.*javascript)^java/i.test(a/**/)?"car":"carpet"

Try it online!

Note: don't trust the highlight as it's incorrect. The real Java, properly interpreted looks like below because \u000A is interpreted in the very first step of the compilation as \n, de facto ending the comment that started with the line comment (//).

//
s->s.matches("(?i)(?!.*javascript)java.*"/*
a=>/(?!.*javascript)^java/i.test(a/**/)?"car":"carpet"

Run as JavaScript

//\u000As->s.matches("(?i)(?!.*javascript)java.*"/*
a=>/(?!.*javascript)^java/i.test(a/**/)?"car":"carpet"

Credits to @CowsQuak for the JS version.

let f=

//\u000As->s.matches("(?i)(?!.*javascript)java.*"/*
a=>/(?!.*javascript)^java/i.test(a/**/)?"car":"carpet"

var a=["java","javafx","javabeans","java-stream","java-script","java-8","java.util.scanner","javascript","java-avascript","javascript-events","facebook-javascript-sdk","javajavascript","jquery","python","rx-java","java-api-for-javascript","not-java"];

for(var s of a) console.log(s.padStart(a.reduce((x,y)=>x.length>y.length?x:y).length) + "=>" + f(s));

How many imaginary bonus points for this answer?

-1 byte thanks to @Nevay in the Java answer.

\$\endgroup\$
6
  • 1
    \$\begingroup\$ This isn't competitive in JavaScript or Java. I'm not even convinced it's a serious contender, which is a requirement for all submissions. \$\endgroup\$
    – Dennis
    Jul 14, 2017 at 1:05
  • 12
    \$\begingroup\$ @Dennis Thank you for your information. However I consider this as a polyglot entry. Is there any rule against polyglot entries when they aren't explicitly requested? I tried to golf this as much as possible. For instance, I tried to put both regexes together, but I couldn't get anything shorter than this (because of the two different albeit similar regexes, and their delimiter). It's also impossible to have the same variable definition because JavaScript doesn't allow a new line between a and =>. I tried to stay in the spirit of golfing. If I did something wrong, please tell me? \$\endgroup\$ Jul 14, 2017 at 10:11
  • 31
    \$\begingroup\$ @Dennis IMHO "Java/JavaScript polyglot" counts as its own language, in which case this is very competitive. \$\endgroup\$ Jul 14, 2017 at 15:29
  • 1
    \$\begingroup\$ @OlivierGrégoire I'm not saying this isn't a well-golfed polyglot submission, but it's debatable if there should be polyglot submissions to non-polyglot challenges in the first place. They came up as part of the Can serious contenders do more than the challenge asks for? discussion, but I don't think there's a clear consensus on this particular topic. Personally, I'm not in favor. \$\endgroup\$
    – Dennis
    Jul 14, 2017 at 16:00
  • 4
    \$\begingroup\$ @Dennis Thank you for your insights, I now understand what you meant. Should this answer be tagged as "non-competitive", according to you? On the other hand, while I'm not speaking for all polyglot answers (this is my first ever), this one has the special meaning that the challenge speaks about both Java and JavaScript, and that the "imaginary bonus points" were explicitly awarded for Java, JavaScript and regex answers before I wrote this answer. Java and regex can be combined, JavaScript and regex can be combined, why not all together? Anyways, I don't mind marking this as non-competitive. \$\endgroup\$ Jul 14, 2017 at 16:23
18
\$\begingroup\$

JavaScript, 50 49 bytes

Saved 1 byte thanks to @ValueInk by rearranging the regex

a=>/javascript|^(?!java)/i.test(a)?"car":"carpet"

Test snippet

let f=

a=>/javascript|^(?!java)/i.test(a)?"carpet":"car"

var a=["java","javafx","javabeans","java-stream","java-script","java-8","java.util.scanner","java-avascript","javascript","javascript-events","facebook-javascript-sdk","javajavascript","jquery","python","rx-java","java-api-for-javascript","not-java"];

for(var s of a) console.log(s.padStart(a.reduce((x,y)=>x.length>y.length?x:y).length) + "=>" + f(s));

\$\endgroup\$
8
  • \$\begingroup\$ I was going to steal your regex but that would have made my answer longer :o nice answer though \$\endgroup\$
    – hyper-neutrino
    Jul 13, 2017 at 16:01
  • \$\begingroup\$ Now we just need a java answer. \$\endgroup\$
    – DJMcMayhem
    Jul 13, 2017 at 16:02
  • \$\begingroup\$ We have a Java answer, but... I came to the roughly same regex... \$\endgroup\$ Jul 13, 2017 at 16:25
  • \$\begingroup\$ alternatively: /^java(?!script)/i \$\endgroup\$
    – mystery
    Jul 13, 2017 at 18:47
  • 1
    \$\begingroup\$ @OlivierGrégoire ah, damn, that one seems unfair \$\endgroup\$
    – mystery
    Jul 13, 2017 at 20:48
15
\$\begingroup\$

Java (OpenJDK 8), 92 82 72 58 57 bytes

s->s.matches("(?i)(?!.*javascript)java.*")?"car":"carpet"

Try it online!

1 byte saved thanks to @Nevay!

\$\endgroup\$
1
  • 2
    \$\begingroup\$ You can omit the caret as String#matches attempts to match the entire string. \$\endgroup\$
    – Nevay
    Jul 13, 2017 at 23:45
11
\$\begingroup\$

C (only calling puts), 131 bytes

f(int*s){char r[]="carpet";~*s&'AVAJ'||(r[3]=0);for(;*s&255;*(int*)&s+=1)~*s&'AVAJ'||~s[1]&'IRCS'||~s[2]&'TP'||(r[3]='p');puts(r);}

It does have its problems, but it passes all of the testcases provided :)

g(int* s)
{
  char r[] = "carpet";
  ~*s&'AVAJ' || (r[3]=0);
  for(;*s & 255; *(int*)&s +=1)
    ~*s&'AVAJ' || ~s[1]&'IRCS' || ~s[2]&'TP' || (r[3]='p');
  puts(r);
}

Imaginary bonus points if your answer uses Java, Javascript, or Regex

well... no thanks

\$\endgroup\$
8
\$\begingroup\$

05AB1E, 21 bytes

lD'¦‚å≠sη'îáå*„¾„ƒ´#è

Try it online!

\$\endgroup\$
1
  • 2
    \$\begingroup\$ lD“¦‚“åi“¾„“ë“îá“åi…carë 3 bytes more and 1 hour late :(. Nice job. \$\endgroup\$ Jul 13, 2017 at 17:14
8
\$\begingroup\$

Python 2, 68 bytes

k=input().lower();print'car'+'pet'*(k[:4]!='java'or'javascript'in k)

Try it online!

-11 bytes thanks to notjagan
-2 bytes thanks to Dennis

\$\endgroup\$
9
  • \$\begingroup\$ 11 bytes shorter. \$\endgroup\$
    – notjagan
    Jul 13, 2017 at 15:55
  • \$\begingroup\$ Slightly different 81 byte solution \$\endgroup\$
    – Justin
    Jul 13, 2017 at 19:23
  • \$\begingroup\$ @Justin That too. Nice. \$\endgroup\$
    – hyper-neutrino
    Jul 13, 2017 at 20:10
  • \$\begingroup\$ If you switch to Python 2, you can save 2 bytes with a full program. \$\endgroup\$
    – Dennis
    Jul 14, 2017 at 6:50
  • 1
    \$\begingroup\$ @LukeSawczak Oh I didn't even realize that :P I was using Java right before that and in Java ; is required so I since I have to use it anyway the newline is unnecessary :P That's why I used it. \$\endgroup\$
    – hyper-neutrino
    Jul 14, 2017 at 18:31
4
\$\begingroup\$

C#, 80 78 bytes

s=>(s=s.ToLower()).StartsWith("java")&!s.Contains("javascript")?"car":"carpet"
\$\endgroup\$
2
  • 1
    \$\begingroup\$ I think the most readable language here is C# \$\endgroup\$
    – sepehr
    Jul 14, 2017 at 16:52
  • 2
    \$\begingroup\$ @sepehr You mean you see sharp with C#. (Do I get a bonus for dumb comments) \$\endgroup\$
    – Ray
    Jul 15, 2017 at 9:43
4
\$\begingroup\$

EXCEL Google Sheets, 89 86 Bytes

Saved 3 bytes thanks to Taylor Scott

=LEFT("carpet",6-3*ISERR(SEARCH("javascript",A1))+3*ISERR(IF(SEARCH("java",A1)=1,1,1/0

Takes an input on A1

Explanation

=LEFT("carpet",6-3*ISERR(SEARCH("javascript",A1))+3*ISERR(IF(SEARCH("java",A1)=1,1,1/0)))

 SEARCH("javascript",A1)        #Case-Insensitive Find, returns error if not found  
 ISERR(                         #Returns string true if error, False if not
 3*ISERR(                       #Forces TRUE/False as integer, multiplies by 3
 IF(SEARCH("java",A1)=1,1,1/0)  #If java found, returns integer. if 1, java begins string
                                #so returns 1, which will be turned into 0 by iserr.
                                #Else returns 1/0, which will be turned into 1 by iserr.
 LEFT(                          #Returns digits from the left, based upon count.
\$\endgroup\$
4
  • \$\begingroup\$ I believe that you can replace the Searches with Finds for -2 bytes and that that could be further translated to a google sheets formula for -3 bytes by not closing the last three parens \$\endgroup\$ Jul 13, 2017 at 21:19
  • 1
    \$\begingroup\$ Find is case sensitive, search is case insensitive. But those last 3 bytes are a good idea! \$\endgroup\$
    – Mark
    Jul 13, 2017 at 21:29
  • \$\begingroup\$ Why the swap from Excel to Google Sheets? \$\endgroup\$
    – Stevoisiak
    Jul 13, 2017 at 23:09
  • 2
    \$\begingroup\$ Removing the last 3 parens saves 3 bytes. Excel would just throw an error and put them in for you anyways. \$\endgroup\$
    – Mark
    Jul 13, 2017 at 23:39
4
\$\begingroup\$

Jelly, 27 bytes

,“Ẋṣ“®Ẓȷ»ŒlwЀ/Ḅn2‘×3“¢Ẹị»ḣ

Try it online!

\$\endgroup\$
3
\$\begingroup\$

vim, 58 bytes

gUU:s/.*JAVASCRIPT.*/Q/g
:s/^JAVA.*/car
:s/[A-Z].*/carpet

Try it online!

\$\endgroup\$
1
  • \$\begingroup\$ I think using the g command might be a little shorter, something like :g/\cjavascript/d :g!/^\cjava/d icarpet␛:s/pet..*. \$\endgroup\$
    – Neil
    Jul 15, 2017 at 23:48
3
\$\begingroup\$

Ruby, 42+1 = 43 bytes

Uses the -p flag.

$_="car#{"pet"if~/javascript|^(?!java)/i}"

Try it online!

\$\endgroup\$
3
\$\begingroup\$

Retina,  44  37 bytes

Ai`^(?!.*javascript)java
.+
pet
^
car

Thanks to @MartinEnder for golfing off 7 bytes!

Try it online!

\$\endgroup\$
0
3
\$\begingroup\$

Common Lisp, 131 125 bytes

(lambda(s)(format()"car~@[pet~]"(or(<(length s)4)(not(#1=string-equal"java"(subseq s 0 4)))(search"javascript"s :test'#1#))))

Try it online!

Size reduced thanks to the #n= “trick” of Common Lisp.

Explanation

(lambda (s)                 ; anonymous function
  (format                   ; use of format string to produce the result
    ()                      ; the result is a string
    "car~@[pet~]"           ; print "car", then print "pet" when:
    (or (< (length s) 4)    ; the string is less then 4 characters or
        (not (string-equal "java" (subseq s 0 4)))     ; does not start with java or
        (search "javascript" s :test 'string-equal)))) ; contains javascript
\$\endgroup\$
2
\$\begingroup\$

Python 2, 69 bytes

f=input().lower().find
print'car'+'pet'*(f('java')!=~f('javascript'))

Currently 1 byte longer than the shortest Python 2 solution.

Try it online!

\$\endgroup\$
2
\$\begingroup\$

C (tcc), 144 136 bytes

a;f(s){char*t=s;for(;*t;a=!strncmp(s,"java",4))*t=tolower(*t++);for(t=s;*t;)s=strncmp(t++,"javascript",10)&&s;puts(a*s?"car":"carpet");}

Try it online!

Unrolled:

a;
f(s)
{
    char *t = s;
    for (; *t; a = !strncmp(s, "java", 4))
        *t = tolower(*t++);
    for (t=s; *t;)
        s = strncmp(t++, "javascript", 10) && s;
    puts(a*s ? "car"  :"carpet");
}
\$\endgroup\$
1
\$\begingroup\$

JAISBaL, 36 bytes

℠℘(?!.*javascript)^java.*}͵Ucar½Upet

Verbose/explanation:

# \# enable verbose parsing #\
tolower                           \# [0] convert the top value of the stack to lowercase #\
split (?!.*javascript)^java.*}    \# [1] split the top value of the stack by (?!.*javascript)^java.*} #\
arraylength                       \# [2] push the length of the array onto the stack #\
print3 car                        \# [3] print car #\
!if                               \# [4] if the top value on the stack is falsy, skip the next statement #\
print3 pet                        \# [5] print pet #\

JAISBaL was my first attempt at designing a golfing language, so it's rather quirky... there's no matches or contains, regex or otherwise, so instead we have to split and check the resulting array length... because JAISBaL has a split-by-regex... but no other regex support.... because reasons.

Regex stolen borrowed from @Cows Quack's answer.

\$\endgroup\$
1
\$\begingroup\$

Excel, 84 bytes

="car"&IF(AND(ISERR(SEARCH("javascript",A1)),IFERROR(SEARCH("java",A1),2)=1),,"pet")
\$\endgroup\$
1
\$\begingroup\$

Excel VBA, 76 Bytes

Anonymous VBE immediate window function that takes input from range [A1] and outputs is car/carpet status to the VBE immediate window

Does not use RegExp

?"car"IIf(InStr(1,[A1],"Java",1)*(InStr(1,[A1],"JavaScript",1)=0),"","pet")
\$\endgroup\$
1
  • 1
    \$\begingroup\$ Nice use of vba! I thought a macro would have been shorter. Now I have proof. \$\endgroup\$
    – Mark
    Jul 14, 2017 at 6:24
1
\$\begingroup\$

Python 3, 95 bytes

g=lambda s:(lambda r:'car' if r[:4]=='java' and 'javascript' not in r else 'carpet')(s.lower())

Try it online!

Yeah, it could be shorter but I wanted to try using a nested lambda!

\$\endgroup\$
1
  • \$\begingroup\$ Always good to experiment :) Note that you can save bytes around operators like and, or, if, else \$\endgroup\$ Jul 14, 2017 at 18:31
1
\$\begingroup\$

Perl, 42 bytes

I believe the answer by stevieb has an incorrect output (tried that one myself - it returns car for 'javajavascript'). This should work:

say/^java/i&&!/javascript/i?'car':'carpet'
\$\endgroup\$
1
\$\begingroup\$

Bracmat, 66 bytes

(f=.pet:?b&@(low$!arg:(? javascript ?|java ?&:?b|?))&str$(car !b))

Try it online!

\$\endgroup\$
1
\$\begingroup\$

Go, 134 bytes

import."strings"
func f(s string)string{T,o:=ToLower,"car"
if Contains(T(s),"javascript")||!HasPrefix(T(s),"java"){o+="pet"}
return o}

Attempt This Online!

\$\endgroup\$
1
\$\begingroup\$

Lua, 88 bytes

s=io.read():lower()print(s:sub(1,4)=='java'and not s:find'javascript'and'car'or'carpet')

Attempt This Online!

\$\endgroup\$
2
  • \$\begingroup\$ Fails for input Javascript, but moving the call to :lower() to just after io.read() seems to fix it. Also, you can save 3 bytes by removing the whole concatenation of 'car' and just doing and'car'or'carpet'. \$\endgroup\$
    – noodle man
    Nov 12, 2023 at 0:40
  • \$\begingroup\$ Just FYI this is still wrong after your edit, the :lower() needs to be moved to just after io.read() so cases like JAVASCRIPTING -> carpet work correctly \$\endgroup\$
    – noodle man
    Nov 12, 2023 at 16:47
1
\$\begingroup\$

GolfScript, 53 49 44 bytes

{32|}%"java"/(,\{6<"script"=+}/"carpet".3<if

Try it online!

This was my second GolfScript submission so after writing a couple more I was able to revisit this and shave a couple bytes.

Previously, this mapped over a list, then summed it, then added it to a base value. Now, it just loops over the list, adding to the base value on each iteration.

Here's an explanation of how the code works:

{32|}%           # Convert the string to lowercase

"java"/          # Split on "java".
(,               # Extract the first item, and push its length
                 # (0 iff string starts with java).
\                # Swap so the rest of the list is on top of the stack.

{6<"script"=+}/  # Check if any start with "script":
{            }/  #   Loop over each item:
 6<              #     Take the first 6 characters.
   "script"=     #     Are they equal to "script"? (0 or 1)
            +    #     Add this to the top of the stack.

# After this loop, the stack will be 0 iff the string started
# with "java" and does not contain "javascript".

"carpet".3<     # Push "carpet" and its first 3 characters.
if              # If the value is 0, "car", otherwise "carpet".
\$\endgroup\$
0
\$\begingroup\$

Mathematica, 82 bytes

regex

If[#~StringMatchQ~RegularExpression@"(?i)(?!.*javascript)^java.*","Car","Carpet"]&
\$\endgroup\$
0
\$\begingroup\$

Batch, 91 bytes

@set/ps=
@set t=%s:~0,4%
@if "%t:java=%%s:javascript=%"=="%s%" (echo car)else echo carpet

Takes input on STDIN. Batch doesn't have a case insensitive comparison operator but it does have case insensitive string replacement so I can assign a temporary to the first four characters and then case insensitively replace java, which should then result in the empty string. Meanwhile I case insensitively replace javascript in the original string, which should leave it unchanged.

\$\endgroup\$
0
\$\begingroup\$

Lua, 96 bytes

function(x)return x:lower():match"^java"and not x:lower():match"javascript"and"car"or"carpet"end
\$\endgroup\$
0
\$\begingroup\$

Perl, 98 84 62 Bytes

sub a{"car".($_[0]=~/javascript/i||$_[0]!~/^java/i?'pet':'');}

Try it online!

Thanks to bytepusher

\$\endgroup\$
5
  • \$\begingroup\$ Welcome to the site! I don't know any perl, but it looks like there is a lot of whitespace you could remove. Also, if you're looking for more ways to shorten it, there's a bunch of tips here. \$\endgroup\$
    – DJMcMayhem
    Jul 13, 2017 at 18:04
  • \$\begingroup\$ @DJMcMayhem Thank you, I think the entire logic can be changed to make it even shorter, but I haven't figured it out \$\endgroup\$
    – Burgan
    Jul 13, 2017 at 18:28
  • 1
    \$\begingroup\$ Just some hints (without changing your solution too much): You can replace the return $b; with just $b;. Perl always returns the last evaluated statement. Since we don't care about warnings, you can even drop the ';' to $b}. You don't need the brackets around the if. If you use || instead of or, you can save a whitespace after the regex. \$\endgroup\$
    – bytepusher
    Jul 16, 2017 at 15:45
  • 1
    \$\begingroup\$ You can also remove the () around the first lc, but need a space after if then. If you use !~ instead of ! =~ the second condition can be lc$_[0]!~. ` -> sub a{$b="car";$b.="pet"if lc$_[0]=~/javascript/||lc$_[0]!~/^java/;$b}. Using the ternary ops brings it down one more sub a{$b="car";$b.="pet"if lc$_[0]=~/javascript/||lc$_[0]!~/^java/;$b} \$\endgroup\$
    – bytepusher
    Jul 16, 2017 at 15:53
  • 1
    \$\begingroup\$ Not to forget - no need for lc when you have the regex ignore case switch, down another 2 :) $_[0] =~//i||$_[0]!~//i. And finally, why a variable? sub a{"car".($_[0]=~/javascript/i||$_[0]!~/^java/i?'pet':'');} should do fine :). And now: perl will be nice and let you use $_[0] w/o specifying it (though not with !~): sub a{"car".(/javascript/i||!/^java/i?'pet':'')} -> 48 :) \$\endgroup\$
    – bytepusher
    Jul 16, 2017 at 15:58
0
\$\begingroup\$

Dart VM, 104 bytes 102 bytes

main(p){p=p[0].toLowerCase();print("car${p.indexOf('java')==0&&p.indexOf('javascript')<0?'':'pet'}");}

Explanation:

Degolfed:

main(p)
{
    p = p[0].toLowerCase();
    print("car${p.indexOf('java') == 0 && p.indexOf('javascript') < 0 ? '' : 'pet'}");
}

We have our usual main function

We replace p with p[0].toLowerCase(); so that we don't have to declare a new variable (var plus a space would be 4 extra bytes)

We then proceed to do the actual printing

We print car unconditionally and we use inline statements for checking whether to print pet after it or not. If it has the string 'java' at index 0 and does not have 'javascript' in it, we do nothing (we actually append an empty string but it does not have any effect) and otherwise we append pet.

\$\endgroup\$
0
\$\begingroup\$

Rust, 97 bytes

let s=if Regex::new(r"^javascript|^!java$").unwrap().is_match("javascript"){"carpet"}else{"car"};

I'm pretty sure that there is a shorter solution but it's my first try :)

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.