webForumDet fria alternativet

Läsa slumpvis rad i textfil

JavaScriptur Javascript

27 svar · 1 733 visningar · startad av Fuel

Medlem sedan okt. 20001 285 inlägg
Frågan#1

Behöver en snutt som läser en slumvis rad i en textfil och sen tar ut raden i en array. Exempel textfil..

hejsvejsan, yyyyyyyg
ggggggggg, hhhhhhhh
blah blahgi, xxxxxxxxxi
asdfassdfd, mmmmmm

säg att den slumpar fram rad 2, alltså hittade[0] = ggggggggg och hittade[1] = hhhhhhhh

Är det samma som i php ? gärna kodexempel, tackar & bockar på förhand.

Medlem sedan mars 200741 inlägg
#2

<?php
$data = file('datafil.txt');
$rows=sizeof($data);
$r=rand(0,$rows-1);
$selectedRow=explode(',',$data[$r);

// slumpradens slots = selectedRow[0], selectedRow[1], ... etc.

?>

Medlem sedan okt. 20001 285 inlägg
#3

??? Det där ÄR php

Medlem sedan aug. 20039 340 inlägg
#4

Fuel, hur tänker du dig att du ska läsa en fil i JS?

Medlem sedan mars 200741 inlägg
#5

Ursäkta. Drabbades av kortslutning. :)

Det går faktiskt att låta javascript läsa textfiler från servern med hjälp av ajaxteknik men det är helt hopplöst att få svenska bokstäver ÅÄÖ att fungera.

Vad man får göra är något skript på serversidan som läser filen och kodar om alla konstiga tecken sen får javascriptet koda tillbaka det.

Det blir lite halvmekigt och eftersom ajax inte når ut riktigt till 100% så blir det inte heller alla som kan del av det.

Du skriver "en liten snutt" och då låter det ju som du förväntar dig något busenkelt ... men vill du ha det i javaskript lär det bli mer än några rader.

Medlem sedan juni 20014 421 inlägg
#6

Via xmlhttprequest? ;)

function doStuff(strStuff){
arrLines=strStuff.split("\n");
arrVal = arrLines[Math.floor(Math.random() * (arrLines.length+1))].split(",");
alert(arrVal[0]);
alert(arrVal[1]);
}

var xhr = new XMLHttpRequest();
xhr.open("GET", "fil.txt");
xhr.onreadystatechange = function() {
  if (xhr.readyState == 4) {
   txt= xhr.responseText;
   doStuff(txt);
  }
}
xhr.send(null);

filen i fråga kan se ut såhär:

Rad1värde1,Rad1värde2
Rad2värde1,Rad2värde2
Rad3värde1,Rad3värde2
Rad4värde1,Rad4värde2
Medlem sedan mars 200741 inlägg
#7

colione:

Du har illustrerat principen. Då återstår bara att få det att fungera och bli kompatibelt också. Jag kan bidra med lite kod så får andra hjälpa till med ÅÄÖ -biten.

Lägg till nedanstående funktion och byt ut new XMLHttpRequest i colione's kod mot getHttpRequest();

function getHttpRequest()
{
	var handle = false;

	if (window.XMLHttpRequest) 
	{
		handle = new XMLHttpRequest();
		if(handle.overrideMimeType) // Mozilla/Safari/IE7+
		{
			handle.overrideMimeType('text/xml; charset=iso-8859-1'); 
		}
	} 
	else 
	if (window.ActiveXObject) 
	{
		try 
		{
			handle = new ActiveXObject("Msxml2.XMLHTTP");
		} 
		catch (e) 
		{
			try 
			{
				handle = new ActiveXObject("Microsoft.XMLHTTP");
			} 
			catch (e) {}
		}
	}

	if (!handle) 
	{
		return false;
	}

	return handle;
}
Medlem sedan aug. 20039 340 inlägg
#8

Två kommentarer här:
colione: Uttrycket du använder för att slumpa index kan skrivas enklare som parseInt(Math.random()*arrLines.length)
Du behöver i detta fall inte göra det gamla tricket att justera med +1 och sedan använda en floor-funktion.
coder: Det borde väl gå jättebra att få ÅÄÖ & co att funka om man strikt håller sig till UTF-8 överallt? Eller krånglar det ändå? (Om textfilen inte är skriven i UTF-8 blir det väl till att skriva/använda en konverterare i valfritt serverspråk)

Medlem sedan mars 200741 inlägg
#9

nitro2k01 skrev:

coder: Det borde väl gå jättebra att få ÅÄÖ & co att funka om man strikt håller sig till UTF-8 överallt? Eller krånglar det ändå? (Om textfilen inte är skriven i UTF-8 blir det väl till att skriva/använda en konverterare i valfritt serverspråk)

Jo. Precis det borde ju fungera.

Jag hade dock grymma problem med detta i något projekt för något år sedan.

Men i teorin:

Om man på serversidan låter ett skript läsa filen och trycka ut den och är noga med att sätta header("Content-type: text/html; charset=utf-8"); (för php) eller Response.Charset="utf-8" (asp) så borde fungera.

Medlem sedan juni 20014 421 inlägg
#10

nitro2k01 skrev:

Två kommentarer här:
colione: Uttrycket du använder för att slumpa index kan skrivas enklare som parseInt(Math.random()*arrLines.length)
Du behöver i detta fall inte göra det gamla tricket att justera med +1 och sedan använda en floor-funktion.

Så sant, jag återanvände en gammal slump-funktion jag hade, därav var det kvar.

Medlem sedan okt. 20001 285 inlägg
#11

Tack alla..

Hur markera man nu 2 st som lösning ? :) colione + coders

Hur är det med browser support? IE6 & FF1.5 som lägst?

Jag har verkligen dammiga javascript kunskaper.. vad är try & catch?

Medlem sedan dec. 2004736 inlägg
#12

Skriver i C# och pratar därför om ett program istället, ska ju bara ge bilden.
Man får inte dividera med 0, vilket jag gör nedan. Med try...catch så "fångar" jag felet i catch och behandlar det där. Jag skulle kunna skriva en rad om att "Så fick du inte göra!" istället för att allt kraschar och man får upp ett Windowsmeddelande om fel och programmet avslutas.

try
{
int division = 0;
int i = 100 / division;
}
catch (Exception ex)
{
//Division med noll inte tillåten! Men programmet fortsätter köras
}

Medlem sedan juni 20014 421 inlägg
#13

Mozillas developer sidor är väldigt bra när det gäller funktions-frågor. Ofta finns det även guider och exempel på implementation:

http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Guide:Exception_Handling_Statements:try...catch_Statement

Medlem sedan okt. 20001 285 inlägg
#14

Ibland blir det bara tomt, vad beror det på ?

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="sv" lang="sv">
<head>
<meta http-equiv="pragma" content="no-cache" />
<meta http-equiv="cache-control" content="no-cache" />
<script type="text/javascript"><!--//--><![CDATA[//><!--
function getHttpRequest()
{
	var handle = false;

	if (window.getHttpRequest) {
		handle = new getHttpRequest();
		if(handle.overrideMimeType) // Mozilla/Safari/IE7+
		{
			handle.overrideMimeType('text/xml; charset=iso-8859-1'); 
		}
	} else if (window.ActiveXObject) {
		try 
		{
			handle = new ActiveXObject("Msxml2.XMLHTTP");
		} 
		catch (e) 
		{
			try 
			{
				handle = new ActiveXObject("Microsoft.XMLHTTP");
			} 
			catch (e) {}
		}
	}

	if (!handle) 
	{
		return false;
	}

	return handle;
}

function doStuff(strStuff)
{
	arrLines=strStuff.split("\n");
	arrVal = arrLines[Math.floor(Math.random() * (arrLines.length+1))].split(",");
	document.getElementById('visa').innerHTML = arrVal[0] + " - " + arrVal[1];
}

function omg()
{
	var xhr = new XMLHttpRequest();
	xhr.open("GET", "fil.txt");
	xhr.onreadystatechange = function() {
		if (xhr.readyState == 4) {
			txt= xhr.responseText;
			doStuff(txt);
		}
	}
	xhr.send(null);
}
//--><!]]></script>
<style type="text/css"><!--/*--><![CDATA[/*><!--*/
body {
	
}
#visa {
	border: 1px solid #000000;
	padding: 3px;
}
/*]]>*/--></style>
<title>Test</title>
</head>
<body>
<h1>Test</h1>
<div id="visa"></div>
<script type="text/javascript"><!--//--><![CDATA[//><!--
omg();
//--><!]]></script>
</body>
</html>

Kan jag ändra arrLines.length+1 till arrLines.length kanske ?

Hepp.. det fungerar inte alls i Internet Exploder..

Medlem sedan juni 20014 421 inlägg
#15

Såhär ska det se ut: (även ändrat slumpfunktionen till parseInt)

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="sv" lang="sv">
<head>
<meta http-equiv="pragma" content="no-cache" />
<meta http-equiv="cache-control" content="no-cache" />
<script type="text/javascript"><!--//--><![CDATA[//><!--
function getHttpRequest()
{
	var handle = false;

	if (window.XMLHttpRequest) {
		handle = new XMLHttpRequest();
		if(handle.overrideMimeType) // Mozilla/Safari/IE7+
		{
			handle.overrideMimeType('text/xml; charset=iso-8859-1'); 
		}
	} else if (window.ActiveXObject) {
		try 
		{
			handle = new ActiveXObject("Msxml2.XMLHTTP");
		} 
		catch (e) 
		{
			try 
			{
				handle = new ActiveXObject("Microsoft.XMLHTTP");
			} 
			catch (e) {}
		}
	}

	if (!handle) 
	{
		return false;
	}

	return handle;
}

function doStuff(strStuff)
{
	arrLines=strStuff.split("\n");
	arrVal = arrLines[parseInt(Math.random() * (arrLines.length))].split(",");
	document.getElementById('visa').innerHTML = arrVal[0] + " - " + arrVal[1];
}

function omg()
{
	var xhr = new getHttpRequest();
	xhr.open("GET", "fil.txt");
	xhr.onreadystatechange = function() {
		if (xhr.readyState == 4) {
			txt= xhr.responseText;
			doStuff(txt);
		}
	}
	xhr.send(null);
}
//--><!]]></script>
<style type="text/css"><!--/*--><![CDATA[/*><!--*/
body {
	
}
#visa {
	border: 1px solid #000000;
	padding: 3px;
}
/*]]>*/--></style>
<title>Test</title>
</head>
<body>
<h1>Test</h1>
<div id="visa"></div>
<script type="text/javascript"><!--//--><![CDATA[//><!--
omg();
//--><!]]></script>
</body>
</html>

Att det blir tomt tror jag beror på hur din fil ser ut. :)

Nu skapas xmlhttprequesten genom klassen getHttpRequest(), den var dock felkonstruerad förut så den anropade sig själv oändligt antal gånger. :) Nu är det fixat. Funkar även i ie6.

Medlem sedan mars 200741 inlägg
#16

colione skrev:

Nu skapas xmlhttprequesten genom klassen getHttpRequest(), den var dock felkonstruerad förut så den anropade sig själv oändligt antal gånger. :) Nu är det fixat. Funkar även i ie6.

Hur menar du då? Var anropar den sig själv? Däremot undrar jag om det ska stå new framför funktionsanropet:

function omg()
{
	var xhr = [B][red]new[/red][/B] getHttpRequest();
	xhr.open("GET", "fil.txt");

...
Medlem sedan juni 20014 421 inlägg
#17

coder skrev:

Hur menar du då? Var anropar den sig själv? Däremot undrar jag om det ska stå new framför funktionsanropet:

function omg()
{
	var xhr = [B][red]new[/red][/B] getHttpRequest();
	xhr.open("GET", "fil.txt");

...

Felet fanns inte i din kod utan i Fuels kod, han hade tydligen modifierat det hela lite. :)
Varför skulle det inte stå new? :)

Medlem sedan mars 200741 inlägg
#18

colione skrev:

Varför skulle det inte stå new? :)

Därför att objektet redan är skapat i funktionen getHttpRequest(). Nu blir det ju

var xhr = new (new XMLHttpRequest());

Medlem sedan okt. 20001 285 inlägg
#19

hmm..

function omg()
{
	var xhr = getHttpRequest();

Både med och utan "new" fungerar i IE6 & FF2

Medlem sedan juni 20014 421 inlägg
#20

coder skrev:

Därför att objektet redan är skapat i funktionen getHttpRequest(). Nu blir det ju

var xhr = new (new XMLHttpRequest());

Nja, du returnerar ett skapat objekt däremot. Hade du returnerat new XMLHttpRequest() och gjort en new på den hade du fått ett js-fel (du ska få ivf.)

Vad du gör är ju att be webbläsaren skapa dig en ny instans getHttpRequest, denna returnerar i sin tur ett objekt som här placeras i xhr.

142 ms totalt · 3 externa anrop · v20260731065814-full.4bcf49fe
0 ms — hämta forumlista (cache)
0 ms — hämta statistik (cache)
138 ms — hämta tråd, inlägg och bilagor (db)