Consejos para jugar golf en SmileBASIC

11

SmileBASIC merece más atención. Solo he visto 3 usuarios aquí (¡incluido yo mismo!) Que proporcionan respuestas SB, y aunque eso no me sorprende, me decepciona. Ser un idioma pagado y ser un dialecto BÁSICO ciertamente apaga a las personas, pero para quienes lo poseen es bastante flexible y, sorprendentemente, golfable. Supuse que abriría este hilo de consejos y vería qué pasa.

Espero que 12Me21 visite con frecuencia :)

caracol_
fuente

Respuestas:

11

Reemplazar string!=""constring>""

SB le permite hacer comparaciones mayores / menores en cadenas, en función de sus puntos de código. Sin embargo, la cadena vacía se considera la cadena más pequeña que existe.

Entonces, para situaciones en las que lo hace string!="", puede usar uno string>""o ""<string, ya que cada cadena es mayor ""y ""menor que cada cadena. Dependiendo de si usa <o >depende de si la declaración necesita espacios en blanco antes o después para ser una sintaxis válida, lo que también puede ahorrarle bytes.

Por ejemplo:

WHILE S$!=""

se puede convertir en

WHILE S$>""

y más golf a

WHILE""<S$
caracol_
fuente
Todas las cuerdas son verdaderas. Incluso los vacíos.
caracol_
Ah bien. Tiene sentido.
Rɪᴋᴇʀ
6

El uso de ?, ., @, y las cuerdas sin cerrar

Muchos dialectos de soporte BÁSICO ?para la impresión, y SB no es una excepción. Tener una función de salida de texto extremadamente corta es una gran ventaja.

En SmileBASIC, .se evalúa como 0.0, por lo que se puede usar en lugar de 0 para ahorrar espacio. Por ejemplo: SPSET 0,21puede ser SPSET.,21, guardar 1 byte. ( SPSET0,21no es válido porque SPSET0podría ser una función definida por el usuario) EXEC.es una forma extremadamente corta de hacer un bucle de programa para siempre (pero restablece todas sus variables, por lo que no siempre se puede usar)

Las etiquetas (utilizadas para GOTO, GOSUBy lectura DATA) se representan como @LABELen SmileBASIC. Cuando se usan en una expresión, en realidad se tratan como cadenas. Por ejemplo, BGMPLAY"@305C"se puede escribir comoBGMPLAY@305C

Las cadenas se cierran automáticamente al final de una línea (o al final del programa). ?"Hello, World!"se puede escribir como ?"Hello, World!. Esto también se puede utilizar para hacer que los programas sean más legibles dividiéndolos en varias líneas sin cambiar la longitud: ?"Meow"BEEP 69puede ser

?"Meow
BEEP 69
12Me21
fuente
Wow, usar etiquetas para iniciar MML es una locura. Nunca hubiera pensado en eso, aunque limita tu conjunto de personajes.
caracol_
Otro lugar que utilicé fue para verificar si un dígito hexadecimal era un número o una letra: @A<POP(H$)es más corto que "@"<POP(H$)( Ano importa, solo verifica el primer carácter, ya que nunca será el mismo)
12Me21
3

Utilice la indexación de cadenas en lugar de MID$

La MID$función es una función común en muchos BÁSICOS para obtener una subcadena de algún lugar en el medio de una cadena. Sin embargo, si solo necesita obtener el carácter en algún índice, el uso de la indexación de cadenas es mucho más corto. Por ejemplo:

PRINT MID$("ABC",2,1)
PRINT "ABC"[2]

Ambas cadenas de impresión C. admiten la indexación tipo matriz en función de los caracteres, por lo que si solo necesita verificar un carácter a la vez, esta es la mejor manera de hacerlo.

caracol_
fuente
Debería hablar sobre cómo se pueden modificar las cadenas de esta manera. A$=@AA:A$[2]="BD":A$[0]="":A$[2]="C"
12Me21
Probablemente escribiré un conjunto de respuestas sobre cómo las cadenas son básicamente matrices de caracteres, pero aún mejor, porque ponerlo todo en una sola es una gran tarea.
caracol_
... o podrías escribir algo;)
caracol_
No estoy muy familiarizado con cómo funciona en otros idiomas.
12Me21
2

Cuando usar :(o no)

El :personaje se usa como un rompe-declaraciones en SB. Básicamente, lo usa para apilar declaraciones en una línea de la siguiente manera:

PRINT "HELLO!":PRINT "GOODBYE!"

De lo contrario, su estado promedio se rompe con una nueva línea:

PRINT "HELLO!"
PRINT "GOODBYE!"

En realidad, a menudo no es necesario usar el colon en absoluto. Siempre que las declaraciones se puedan dividir en tokens sintácticamente válidos, el analizador tiende a determinar cuándo termina uno y comienza el otro. Lo mismo ocurre a menudo con los espacios en blanco.

PRINT"HELLO!"PRINT"GOODBYE!"

Por supuesto, esto no siempre funciona. Siempre hay casos ambiguos y sintaxis inválidas donde tienes que romper explícitamente las declaraciones. Tomar como ejemplo:

PRINT "HELLO";END

El punto y coma significa que PRINTse espera que se imprima otra expresión, a menos que la instrucción se rompa allí (usamos puntos y comas colgantes para suprimir la nueva línea). Aquí se supone que ENDse supone que es un valor, a pesar de ser una palabra clave, e intenta imprimirlo, resultando en un error Por lo tanto, tenemos que romper explícitamente esta declaración, ya sea los dos puntos o la nueva línea.

En general, si algo parece ambiguo, pruébalo para ver si funciona. Si no es así, rompa la declaración. Además, cualquier cosa que produzca una sintaxis no válida no se resalta correctamente como se menciona en 12Me21.

caracol_
fuente
2

Use el resaltador de sintaxis!

El editor de código de SmileBASIC tiene un resaltador de sintaxis incorporado, que puede usarse para determinar si el código funcionará o no. Por ejemplo, si intenta hacerlo BEEP0, no lo resaltará, porque debe haber un espacio entre una función y un dígito. Sin embargo BEEP.funciona, porque. No es un dígito.

Normalmente, el código like X=7BEEPes válido, ya que las funciones no pueden comenzar con un número, por lo que SB asume eso 7y BEEPestán separadas. Sin embargo. X=7ENDNO está permitido (y no está resaltado), porque intenta interpretarlo 7E...como un número, pero dado que no hay ningún dígito después de la E, falla y causa un error. Normalmente, esto sería bastante difícil de entender, pero con un resaltador de sintaxis muy confiable, es mucho más fácil decir qué puede y qué no puede hacer.

Mi resaltador de sintaxis SmileBASIC está diseñado para (con suerte) coincidir perfectamente con el comportamiento de SB, por lo que puede usarlo para verificar si el código es válido.

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<script src="https://12Me21.github.io/sbhighlight3/sbhighlight.js"></script>
		<link rel="stylesheet" type="text/css" href="https://12Me21.github.io/sbhighlight3/style.css">
		<link rel="stylesheet" type="text/css" href="https://12Me21.github.io/external/smilebasicfont.css">
		<script>
			function update(event){
				$code.textContent=$input.innerText;
				//must be innerText since contentedible and textContent are too dumb to understand linebreaks
				//contenteditable adds <br>s which textContent ignores
				//whyyyyy
				applySyntaxHighlighting($code,true);
			}
			
			function setCaretPosition(elem,caretPos){
				if(elem){
					if(elem.createTextRange) {
						var range=elem.createTextRange();
						range.move('character',caretPos);
						range.select();
					}else{
						if(elem.selectionStart){
							elem.focus();
							elem.setSelectionRange(caretPos,caretPos);
						}else
							elem.focus();
					}
				}
			}
		</script>
		<style>
			#editcontainer{
				position: absolute;
			}
			#editcontainer>pre{
				position: absolute;
				left: 0;
				top: 0;
				
			}
			pre.csssucks *{
				color:transparent !important;
				background-color:transparent !important;
				caret-color: white;
			}
			pre.csssucks {
				color:transparent !important;
				background-color:transparent !important;
				caret-color: white;
				border-color:transparent;
				padding-right: 50ch;
			}
		</style>
	</head>
	<body>
		Use SB font:<input type="checkbox" autocomplete="off" onchange="$code.dataset.sbfont=$input.dataset.sbfont=this.checked;update()"></input>
		<button onclick="update()">force update</button>
		<hr>
		<div id="editcontainer">
			<pre id="$code">test</pre>
			<pre id="$input" class="csssucks" contenteditable="true" spellcheck="false" onkeydown="setTimeout(function(){update(event)},2);">test</pre>
		</div>
	</body>
</html>

12Me21
fuente
1

Evitar el operador MOD

El operador del módulo es realmente largo y debe evitarse si es posible.

Si obtiene caracteres de una cadena, puede repetir la cadena en su lugar:

"ABC"[X MOD 3]
("ABC"*9)[X] (assuming X will always be less than 27)

A veces puedes guardar 1 personaje con AND:

X MOD 4
3AND X
12Me21
fuente
0

Omitir OUTvalores de retorno

Una OUTfunción de formulario es una con múltiples retornos; Usted especifica las variables para aceptar los valores de retorno después de la OUTpalabra clave. Un ejemplo usando DTREAD:

DTREAD OUT yearVar,monthVar,dayVar

Pero, ¿qué sucede si solo desea uno de los valores, como el mes actual? ¡Puede "ignorar" el resto de los valores simplemente no escribiendo ningún nombre de variable para aceptarlos! Sin embargo, debe salir en las comas (aparte de la devolución opcional ocasional).

DTREAD OUT ,monthVar,

Que se puede seguir jugando al golf

DTREAD OUT,M,
caracol_
fuente
0

Utilizar LAST()

Ahora que SmileBASIC 4 está disponible en Japón, podemos ver algunos de los posibles ahorros de golf. Uno que me llama la atención de inmediato es la nueva LAST()función, que devuelve el último índice de una matriz o cadena. Puedes guardar un byte.

LEN(v)-1 'old way
LAST(v)  'new way
caracol_
fuente