11
2
This challenge will behave more or less like a traditional code-golf. The only difference is that instead of scoring answers by their number of characters or bytes, users will assign weights to different characters in the comments and the program with the lowest cumulative weight will win.
Challenge
Your task is to write a program that takes a string and prints a diamond shape where the first character starts in the center and subsequent characters occupy the empty spaces orthogonal to the set of characters that were placed last. Spaces () will be used for padding.
For example inputting CAT
would produce
T
TAT
TACAT
TAT
T
and ()
would produce
)
)()
)
and desserts
would produce
s
sts
strts
strerts
streserts
stressserts
stressesserts
stressedesserts
stressed desserts
stressedesserts
stressesserts
stressserts
streserts
strerts
strts
sts
s
and 9
would produce 9
.
Details
The code may only contain printable ASCII and newlines. (See why below.)
Input/output should be via stdin/stdout, or, if they aren't possible, use similar alternatives.
You may assume the input string only contains printable ASCII (including space).
Columns of leading spaces not containing any portion of the diamond pattern are not allowed in the output. Any amount and combination of trailing spaces spaces is allowed.
There may optionally be a trailing newline in the output.
You may edit your answer as much as you want.
Scoring
All code must be written using only newlines and the 95 printable ASCII characters:
!"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~
(Sadly tabs are not allowed because Stack Exchange renders them as spaces in code blocks.)
Each of these 96 characters has a weight value associated with it. By default, all the weights are 97.
The score of a program is the sum of the weight values for each of its characters. For example, if the program were print(4)
and the weight for 4
was 70, but unchanged for everything else, the score would be 749 = 97+97+97+97+97+97+70+97
.
Once the activity in this question settles down to almost nothing, the lowest scoring submission wins. In the presumably unlikely case of tie the wins goes to the highest voted answer.
Changing Weights
Every user, whether they've answered or not, can change the weight of one of the 96 characters to a unique value from 1 to 96. To do this, add a comment to this question of the form #### W -> C ####
, where W is an integer from 1 to 96 and C is the character (as itself, no quotes, no backticks). Use \n
in place of C for newlines and \s
for space since Stack Exchange compresses 3 spaces in a row. The print(4)
example above would have had the comment #### 70 -> 4 ####
.
Each user may only make ONE comment like this, and it will only be valid if both the character and the weight value have not been used in a previously made comment. Thus eventually, there may be 96 #### W -> C ####
comments, all from different users, all with different weights assigned to different characters.
Users may delete their own comment if they want to, resetting their characters' weight back to 97 until they or someone else comments again. They may also edit them. Comments not following the rules about distinct users/weights/characters should be deleted or flagged as "not constructive". General comments about rules and other things are fine but should be kept at a minimum.
This stack snippet is the official leaderboard for this question. It automatically computes the scores for all submissions by gathering the weights from comments each time it is run. It does not handle ties. You can also use it to check the score a program would have.
You'll probably need to right-click -> Open link in new tab
for the links.
function compute(){var e=computeScore($("#code").val());$("#score").val(e==-1?"Invalid characters":e)}function computeScore(e){var t=0;for(var n=0;n<e.length;n++){if(weights.hasOwnProperty(e[n])){t+=weights[e[n]]}else{return-1}}return t}function htmlDecode(e){var t=document.createElement("div");t.innerHTML=e;return t.childNodes.length===0?"":t.childNodes[0].nodeValue}function addLeaderboard(){validAnswers.sort(function(e,t){return e.score>t.score});var e=1;var t="";for(var n=0;n<validAnswers.length;n++){var r=validAnswers[n];t+="<tr><td>"+e+"</td><td><a href='"+r.link+"'>"+r.owner.display_name+"</a></td><td>"+r.score+"</td><td>"+r.length+"</td></tr>";if(n+1<validAnswers.length&&validAnswers[n+1].score>r.score){e++}}$("#leaderboard").append(t)}function addAnalytics(){var e="";for(var t in weights){if(weights.hasOwnProperty(t)&&weights[t]!=defaultWeight){e+=(t=="\n"?"\\n":t)+"="+weights[t]+" "}}$("#weights").val(e);var n="";for(var t in usedChars){if(usedChars.hasOwnProperty(t)&&usedChars[t]==false){n+=t=="\n"?"\\n":t}}$("#unusedc").val(n);var r="";for(var t in usedWeights){if(usedWeights.hasOwnProperty(t)&&usedWeights[t]==false){r+=t+" "}}$("#unusedw").val(r);var i="";if(invalidComments.length>0){for(var s=0;s<invalidComments.length;s++){var o=invalidComments[s];i+="<a href='#"+o.link+"'>"+o.owner.display_name+"</a> "}}else{i="none"}$("#comments").html(i);var u="";if(invalidAnswers.length>0){for(var s=0;s<invalidAnswers.length;s++){var a=invalidAnswers[s];u+="<a href='#"+a.link+"'>"+a.owner.display_name+"</a> "}}else{u="none"}$("#answers").html(u)}function checkAnswers(e){for(var t=0;t<e.items.length;t++){var n=e.items[t];var r=answerPattern.exec(n.body);if(r){var i=htmlDecode(r[1]);var s=computeScore(i);if(s==-1){invalidAnswers.push(n)}else{n.length=i.length;n.score=s;validAnswers.push(n)}}else{invalidAnswers.push(n)}}addLeaderboard();addAnalytics()}function checkComments(e){for(var t=0;t<e.items.length;t++){var n=e.items[t];var r=commentPattern.exec(htmlDecode(n.body));if(r){var i=n.owner.user_id;var s=parseInt(r[1]);var o=r[2]=="\\n"?"\n":r[2]=="\\s"?" ":r[2];if(userIDs.hasOwnProperty(i)||!usedWeights.hasOwnProperty(s)||usedWeights[s]||!usedChars.hasOwnProperty(o)||usedChars[o]){invalidComments.push(n)}else{userIDs[i]=true;usedWeights[s]=true;usedChars[o]=true;weights[o]=s}}}$.get(answersURL,checkAnswers)}function refresh(){$.get(commentsURL,checkComments)}questionID=45040;commentsURL="https://api.stackexchange.com/2.2/questions/"+questionID+"/comments?order=asc&sort=creation&site=codegolf&filter=!t)IWLXOkOvAuPe8m2xJrXOknWcw(ZqZ";answersURL="https://api.stackexchange.com/2.2/questions/"+questionID+"/answers?order=desc&sort=activity&site=codegolf&filter=!.FjsvG2LuND(frE*)WTvqQev1.lyu";commentPattern=/^#### (\d+) -> (\\(?:n|s)|[ -~]) ####$/;answerPattern=/<pre><code>((?:\n|.)*?)\n<\/code><\/pre>/;chars="\n !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~";validAnswers=[];invalidAnswers=[];invalidComments=[];userIDs={};usedWeights={};usedChars={};weights={};defaultWeight=chars.length+1;for(var i=0;i<chars.length;i++){usedChars[chars[i]]=false;usedWeights[i+1]=false;weights[chars[i]]=defaultWeight}refresh()
*{font-family:Helvetica,Arial,sans-serif}table{border:3px solid green;border-collapse:collapse}button{font-size:100%}th{background-color:green;color:#fff;padding:6pt}td{border:1px solid green;padding:6pt}.large{font-size:140%}.title{font-weight:700;margin:6pt 0}textarea{font-family:"Courier New";white-space:nowrap;overflow:auto}input[readonly]{background-color:#dcdcdc}.analytics{font-size:90%;padding:4pt 0 0}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script><div class='large title'>Leaderboard</div><table id='leaderboard'> <tr> <th>Place</th> <th>Submitter</th> <th>Score</th> <th>Program Length</th> </tr></table><br><div class='title'>Compute Score</div><textarea id='code' rows='5' cols='40' placeholder='paste code here...'></textarea><br><button type='button' onclick='compute()'>Compute</button> Score: <input type='text' id='score' readonly><br><br><div class='title'>Analytics</div><div class='analytics'>Assigned weights: <input type='text' id='weights' readonly></div><div class='analytics'>Unused characters: <input type='text' id='unusedc' readonly> (all weight 97)</div><div class='analytics'>Unused weights: <input type='text' id='unusedw' readonly></div><div class='analytics'>Invalid comments (duplicate user/char/weight): <span id='comments'></span></div><div class='analytics'>Invalid answers (illegal characters or no code block): <span id='answers'><span></div><br><button type='button' onclick='refresh'>Refresh</button>
For this leaderboard to work, the comments must be in the exact format described above and your program's code must be in the first multi-line code block in your answer (the <pre><code>...</code></pre>
ones). Don't use syntax highlighting or your code won't be read correctly. The snippet can take a minute or two before it updates.
I have not tested the snippet thoroughly but I'll be keeping an eye on it as this contest gets underway. If you notice any bugs please tell me. Here is an non-minified version:
questionID = 45040
commentsURL = 'https://api.stackexchange.com/2.2/questions/' + questionID + '/comments?order=asc&sort=creation&site=codegolf&filter=!t)IWLXOkOvAuPe8m2xJrXOknWcw(ZqZ'
answersURL = 'https://api.stackexchange.com/2.2/questions/' + questionID + '/answers?order=desc&sort=activity&site=codegolf&filter=!.FjsvG2LuND(frE*)WTvqQev1.lyu'
commentPattern = /^#### (\d+) -> (\\(?:n|s)|[ -~]) ####$/
answerPattern = /<pre><code>((?:\n|.)*?)\n<\/code><\/pre>/
chars = '\n !"#$%&\'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~'
validAnswers = []
invalidAnswers = []
invalidComments = []
userIDs = {}
usedWeights = {}
usedChars = {}
weights = {}
defaultWeight = chars.length + 1
for (var i = 0; i < chars.length; i++) {
usedChars[chars[i]] = false
usedWeights[i + 1] = false
weights[chars[i]] = defaultWeight
}
function compute() {
var score = computeScore($('#code').val())
$('#score').val(score == -1 ? 'Invalid characters' : score)
}
function computeScore(code) {
var score = 0
for(var i = 0; i < code.length; i++) {
if (weights.hasOwnProperty(code[i])) {
score += weights[code[i]]
} else {
return -1
}
}
return score
}
function htmlDecode(input) {
var e = document.createElement('div')
e.innerHTML = input;
return e.childNodes.length === 0 ? '' : e.childNodes[0].nodeValue
}
function addLeaderboard() {
validAnswers.sort(function(a,b) { return a.score > b.score} )
var place = 1
var rows = ''
for(var i = 0; i < validAnswers.length; i++) {
var a = validAnswers[i]
rows +=
'<tr><td>' + place +
"</td><td><a href='" + a.link + "'>" + a.owner.display_name + "</a></td><td>" +
a.score + '</td><td>' + a.length + '</td></tr>'
if (i + 1 < validAnswers.length && validAnswers[i + 1].score > a.score) {
place++
}
}
$('#leaderboard').append(rows)
}
function addAnalytics() {
//assigned weights
var assigned = ''
for (var key in weights) {
if (weights.hasOwnProperty(key) && weights[key] != defaultWeight) {
assigned += (key == '\n' ? '\\n' : key) + '=' + weights[key] + ' '
}
}
$('#weights').val(assigned)
//unused chars
var unusedc = ''
for (var key in usedChars) {
if (usedChars.hasOwnProperty(key) && usedChars[key] == false) {
unusedc += key == '\n' ? '\\n' : key
}
}
$('#unusedc').val(unusedc)
//unused weights
var unusedw = ''
for (var key in usedWeights) {
if (usedWeights.hasOwnProperty(key) && usedWeights[key] == false) {
unusedw += key + ' '
}
}
$('#unusedw').val(unusedw)
//invalid comments
var invalidc = ''
if (invalidComments.length > 0) {
for (var i = 0; i < invalidComments.length; i++) {
var c = invalidComments[i]
invalidc += "<a href='#" + c.link + "'>" + c.owner.display_name + '</a> '
}
} else {
invalidc = 'none'
}
$('#comments').html(invalidc)
//invalid answers
var invalida = ''
if (invalidAnswers.length > 0) {
for (var i = 0; i < invalidAnswers.length; i++) {
var a = invalidAnswers[i]
invalida += "<a href='#" + a.link + "'>" + a.owner.display_name + '</a> '
}
} else {
invalida = 'none'
}
$('#answers').html(invalida)
}
function checkAnswers(answers) {
for (var i = 0; i < answers.items.length; i++) {
var answer = answers.items[i]
var match = answerPattern.exec(answer.body)
if (match) {
var code = htmlDecode(match[1])
var score = computeScore(code)
if (score == -1) {
invalidAnswers.push(answer)
} else {
answer.length = code.length
answer.score = score
validAnswers.push(answer)
}
} else {
invalidAnswers.push(answer)
}
}
addLeaderboard()
addAnalytics()
}
function checkComments(comments) {
for (var i = 0; i < comments.items.length; i++) {
var comment = comments.items[i]
var match = commentPattern.exec(htmlDecode(comment.body))
if (match) {
var userID = comment.owner.user_id
var weight = parseInt(match[1])
var char = match[2] == '\\n' ? '\n' : (match[2] == '\\s' ? ' ' : match[2])
//check validity
if (userIDs.hasOwnProperty(userID) ||
!usedWeights.hasOwnProperty(weight) || usedWeights[weight] ||
!usedChars.hasOwnProperty(char) || usedChars[char])
{
invalidComments.push(comment)
} else {
userIDs[userID] = true
usedWeights[weight] = true
usedChars[char] = true
weights[char] = weight
}
}
}
$.get(answersURL, checkAnswers)
}
function refresh() {
$.get(commentsURL, checkComments)
}
refresh()
* {
font-family: Helvetica, Arial, sans-serif;
}
table {
border: 3px solid green;
border-collapse: collapse;
}
button {
font-size: 100%;
}
th {
background-color: green;
color: white;
padding: 6pt;
}
td {
border: 1px solid green;
padding: 6pt;
}
.large{
font-size: 140%;
}
.title{
font-weight: bold;
margin: 6pt 0 6pt 0;
}
textarea {
font-family: "Courier New";
white-space: nowrap; overflow: auto;
}
input[readonly]
{
background-color: gainsboro;
}
.analytics {
font-size: 90%;
padding: 4pt 0 0 0;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class='large title'>Leaderboard</div>
<table id='leaderboard'>
<tr>
<th>Place</th>
<th>Submitter</th>
<th>Score</th>
<th>Program Length</th>
</tr>
</table>
<br>
<div class='title'>Compute Score</div>
<textarea id='code' rows='5' cols ='40' placeholder='paste code here...'></textarea><br>
<button type='button' onclick='compute()'>Compute</button> Score: <input type='text' id='score' readonly>
<br>
<br>
<div class='title'>Analytics</div>
<div class='analytics'>Assigned weights: <input type='text' id='weights' readonly></div>
<div class='analytics'>Unused characters: <input type='text' id='unusedc' readonly> (all weight 97)</div>
<div class='analytics'>Unused weights: <input type='text' id='unusedw' readonly></div>
<div class='analytics'>Invalid comments (duplicate user/char/weight): <span id='comments'></span></div>
<div class='analytics'>Invalid answers (illegal characters or no code block): <span id='answers'><span></div>
<br>
<button type='button' onclick='refresh'>Refresh</button>
Keep in mind that this scoring system is completely new and experimental. Hopefully Stack Exchange won't mind that it involves tons of comments. :P
Related challenge: Print this diamond
>1 -> *< – Martin Ender – 2015-01-27T12:11:24.980
Comments can be edited for 5 minutes, so allowing them to be edited could cause complete havok with the non-repetition rules. – Peter Taylor – 2015-01-27T12:15:56.143
@PeterTaylor But how can I possibly stop comment edits? Besides totally ignoring ones that are edited. 5 minutes goes pretty fast. – Calvin's Hobbies – 2015-01-27T12:17:06.497
1I don't like this scoring system at all (see chat), but if you're going to use it then ignoring comments which are edited is definitely the right thing to do. – Peter Taylor – 2015-01-27T12:23:15.120
>2 -> :< – Logic Knight – 2015-01-27T12:57:13.087
>3 -> 3< – kennytm – 2015-01-27T13:44:10.970
>5 -> \s< – agweber – 2015-01-27T15:33:32.967
>6 -> (< – Kristoffer Sall-Storgaard – 2015-01-27T15:55:15.580
>7 -> @< – randomra – 2015-01-27T16:22:36.410
>8 -> [< – Zgarb – 2015-01-27T16:28:58.040
>9 -> =< – Alex A. – 2015-01-27T16:42:28.717
>93 -> +< – jimmy23013 – 2015-01-27T17:38:22.393
>94 -> )< – Jørgen R – 2015-01-27T19:31:44.970
>25 -> b< – Jakube – 2015-01-27T20:40:27.887
>95 -> '< – Frxstrem – 2015-01-28T01:39:52.080
stressed desserts
– unclemeat – 2015-01-28T03:21:22.080>4 -> I< – justhalf – 2015-01-28T04:06:46.420
>10 -> $< – Stephen – 2015-01-28T11:18:41.517