Finding min in a stack- Won't print out any result - javascript

Trying to find the min for this stack; however, whenever I run this in JSFiddle nothing prints out... anyone explain to me why? here's the code:
function min_stack() {
var min = 0;
this.elements = [];
this.push = function(element) {
this.elements.push(element);
}
this.pop = function() {
return this.elements.pop();
}
this.min = function() {
min = this.elements[0];
if (this.elements.length > 0) {
for(int i = 0; i < this.elements.length; i++) {
if (min > this.elements[i]) {
min = this.elements[i];
}
}
}
return min;
}
}
var myStack = new min_stack();
myStack.push(5);
myStack.push(4);
myStack.push(3);
print("[" + myStack.elements + "]");
print("min:" + myStack.min());
myStack.pop();
print("[" + myStack.elements + "]");
print("min:" + myStack.min());
myStack.pop();
print("[" + myStack.elements + "]");
print("min:" + myStack.min());

There is a syntax error in your for which shows up immediately in browser console
Change:
for(int i = 0; i < this.elements.length; i++) {
TO
for(var i = 0; i < this.elements.length; i++) {
DEMO: http://jsfiddle.net/y7wET/
ALso as pointed out in comments I doubt you want to use print

int i = 0; is not valid JavaScript. JavaScript does not allow you to specify the type of a variable when declaring it; instead, use var i = 0;.
Also, because "window" is the global object, in the context of the Web page, print() is equivalent to window.print(), which prints the page to your printer.
For debugging purposes, you can pop up a message box using window.alert(); if that is too annoying, you could do something such as adding your output to a textarea element instead.

Related

Right way to dynamically update table

I am getting data over websocket every 10 seconds and i am updating the cells using this function:
agentStatSocket.onmessage = function (e) {
data = JSON.parse(e.data);
//console.log(typeof(data));
for (var i = 0; i < data.length; i++) {
var inboundTd = '#' + data[i]['id'] + '-inbound';
var outboundTd = '#' + data[i]['id'] + '-outbound';
if (data[i]['inboundCalls'] != 0) {
$(inboundTd).html(data[i]['inboundCalls']);
}
if (data[i]['outboundCalls'] != 0) {
$(outboundTd).html(data[i]['outboundCalls']);
}
}
};
This is working pretty fine. However, I see some lag with the table being updated. Currently, there are only 150 rows in the table. I do not know what will be the latency if rows will become 1000 or more.
I have the following questions:
What is the correct approach to design these kinds of tables in which data is changing very frequently? I am not using any library like react or angular. This is plain jQuery.I am using dataTables
jQuery to enhance table view.
One thing to consider is that, in many cases, accessing an element based on an ID is usually a lot quicker in vanilla javascript compared to jquery.
A simple example of that is:
function jsTest() {
for (let i = 0; i < 1000; i++) {
document.getElementById("js").innerHTML = i;
}
}
function jqueryTest() {
for (let i = 0; i < 1000; i++) {
$("#jquery").html(i);
}
}
function startup() {
console.time("javascript");
jsTest();
console.timeEnd("javascript");
console.time("jquery");
jqueryTest();
console.timeEnd("jquery");
}
// For testing purposes only
window.onload = startup;
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
Javascript: <div id="js"></div>
Jquery: <div id="jquery"></div>
So, you could try changing your code to:
agentStatSocket.onmessage = function (e) {
data = JSON.parse(e.data);
//console.log(typeof(data));
for (var i = 0; i < data.length; i++) {
//var inboundTd = '#' + data[i]['id'] + '-inbound';
//var outboundTd = '#' + data[i]['id'] + '-outbound';
var inboundTd = data[i]['id'] + '-inbound';
var outboundTd = data[i]['id'] + '-outbound';
if (data[i]['inboundCalls'] != 0) {
//$(inboundTd).html(data[i]['inboundCalls']);
document.getElementById(inboundTd).innerHTML = data[i]['inboundCalls'];
}
if (data[i]['outboundCalls'] != 0) {
//$(outboundTd).html(data[i]['outboundCalls']);
document.getElementById(outboundTd).innerHTML = data[i]['outboundCalls'];
}
}
};
You can still use jquery for the rest of your code, if you wish, but simple updates to elements that can be targeted by ID are usually quicker with vanilla javascript.

How to set [i] in array?

I don't know to set [i] in the array.
statusResponse() {
var dataStatus = this.$.xhrStatus.lastResponse;
for(var i = 0; i < this.maxStatus; i++) {
console.log(this.maxStatus);
console.log([i]);
console.log(dataStatus);
console.log(dataStatus[fs_+ i +_P41001_W41001B]);
this.userInfo.status({
"branch_plant": this.$.xhrStatus.lastResponse.fs_ +
[i] +_P41001_W41001B.data.gridData.rowset[0].sDescription_99.value
});
}
}
You could change:
dataStatus[fs_+ i +_P41001_W41001B]
to
dataStatus["fs_" + i + "_P41001_W41001B"]
Explaination
This is roughly how the computer understands it the following line:
Take string "fs_"
Add the variable i to it, so the string become "fs_4" (if i = 4)
Add "_P41001_W41001B" to it, so the string becomes "fs_4_P41001_W41001B"
Get dataStatus["fs_4_P41001_W41001B"]
Updated code:
statusResponse() {
var dataStatus = this.$.xhrStatus.lastResponse;
for(var i = 0; i < this.maxStatus; i++) {
console.log(this.maxStatus);
console.log([i]);
console.log(dataStatus);
console.log(dataStatus["fs_" + i + "_P41001_W41001B"]);
this.userInfo.status({
"branch_plant": this.$.xhrStatus.lastResponse["fs_" + i + "_P41001_W41001B"].data.gridData.rowset[0].sDescription_99.value
});
}
}

Getting an infinite loop and can't see why - Javascript

I'm writing a simple little Connect 4 game and I'm running into an infinite loop on one of my functions:
var reds = 0;
var greens = 0;
function checkEmpty(div) {
var empty = false;
var clicked = $(div).attr('id');
console.log(clicked);
var idnum = parseInt(clicked.substr(6));
while (idnum < 43) {
idnum = idnum + 7;
}
console.log("idnum=" + idnum);
while (empty == false) {
for (var i = idnum; i > 0; i - 7) {
idnumStr = idnum.toString();
var checking = $('#square' + idnumStr);
var str = checking.attr('class');
empty = str.includes('empty');
console.log(empty);
var divToFill = checking;
}
}
return divToFill;
}
function addDisc(div) {
if (reds > greens) {
$(div).addClass('green');
greens++;
console.log("greens=" + greens);
} else {
$(div).addClass('red');
reds++;
console.log("reds=" + reds);
};
$(div).removeClass('empty');
}
$(function() {
var i = 1;
//add a numbered id to every game square
$('.game-square').each(function() {
$(this).attr('id', 'square' + i);
i++;
//add an on click event handler to every game square
//onclick functions
$(this).on('click', function() {
var divToFill = checkEmpty(this);
addDisc(divToFill);
})
})
})
Here is a link to the codepen http://codepen.io/Gobias___/pen/xOwNOd
If you click on one of the circles and watch the browser's console, you'll see that it returns true over 3000 times. I can't figure out what I've done that makes it do that. I want the code to stop as soon as it returns empty = true. empty starts out false because I only want the code to run on divs that do not already have class .green or .red.
Where am I going wrong here?
for (var i = idnum; i > 0; i - 7);
You do not change the i.
Do you want to decrement it by 7?
Change your for loop to the one shown below:
for (var i = idnum; i > 0; i -= 7) {
// ...
}
You also do not use loop variable in the loop body. Instead, you use idnum, I think this can be issue.
while (empty == false) {
for (var i = idnum; i > 0; i -= 7) {
idnumStr = i.toString(); // changed to i
var checking = $('#square' + idnumStr);
var str = checking.attr('class');
empty = str.includes('empty');
console.log(empty);
var divToFill = checking;
// and don't forget to stop, when found empty
if (empty) break;
}
}
I add break if empty found, because if we go to next iteration we will override empty variable with smallest i related value.
You can also wrap empty assignment with if (!empty) {empty = ...;} to prevent this override, but I assume you can just break, because:
I want the code to stop as soon as it returns empty = true
Offtop hint:
while (idnum < 43) {
idnum = idnum + 7;
}
can be easy replaced with: idnum = 42 + (idnum%7 || 7)
Change to this:
for (var i = idnum; i > 0; i = i - 7) {
You are not decrementing the i in your for loop
Building on what the others have posted You would want to change the value of empty inside the for loop. because obviously the string still checks the last string in the loop which would always return false.
while(empty==false){
for (var i = idnum; i > 0; i -= 7) {
// your other codes
if (!empty) {
empty = str.includes('empty');
}
}

Console.log not working within my function

So I'm trying to test my code out by applying a console.log in different parts of it. But when I try it in a certain function, it doesn't work. I've tried putting alerts within that function as well to see whether its just a problem with console.log, but alerts don't seem to run either.
Here's my code
var mqrule;
var lines;
var width;
console.log("Nothing");
//HASHMAP BEGINNING HERE
var newKey, newValue;
var MQHash = {};
MQHash[newKey] = newValue;
(function () {
console.log("Nothing");
//FROM HERE, CONSOLE.LOG DOESN'T SEEM TO BE WORKING.
var mqEvents = function (mediaChangeHandler) {
var sheets = document.styleSheets,
numSheets = sheets.length,
mqls = {},
mediaChange = function (mql) {
console.log(mql);
}
if (mediaChangeHandler) {
mediaChange = mediaChangeHandler;
}
for (var i = 0; i < numSheets; i += 1) {
var rules = sheets[i].cssRules,
numRules = rules.length;
console.log("RULES: " + rules);
for (var j = 0; j < numRules; j += 1) {
if (rules[j].constructor === CSSMediaRule) {
mqrule = rules[j].cssText;
console.log(mqrule);
lines = (mqrule).split('\n');
console.log(lines[1]);
mqls['mql' + j] = window.matchMedia(rules[j].media.mediaText);
mqls['mql' + j].addListener(mediaChange);
mediaChange(mqls['mql' + j]);
}
}
}
}
//IT STARTS TO WORK AGAIN FROM HERE THOUGH.
window.mqEvents = mqEvents;
}());
handleMediaChange = function (mql) {
console.log();
var medias = mql.media;
}
Any Suggestions? Thanks in advance. Sorry if this question isn't worded properly!
OK I've figured it out thanks to you guys! I needed to call the function, which I so stupidly had forgotten to do, so I had added;
mqEvents(handleMediaChange);
at the bottom to call mqEvents.
Thanks all!

dat.GUI create multiple buttons with same name

I try to use dat.GUI to create multiple buttons all with same name "ShowCoord", is this possible? What I have currently is:
for (i = 0; i < overlay.numElements; i ++)
{
var length = overlay.elementNumVertices[i];
var subObj = {
'name' : overlay.elementNames[i],
'index' : i,
'numVertices': overlay.elementNumVertices[i],
"ShowCoord" : function(){
console.log("i is " + subObj['index']);
var verts = overlay.elementVertices[i];
for(var j = 0; j < subObj['numVertices']; j ++)
{
console.log("The coordinates are " + verts[3*j] + ", "+ verts[3*j+1] +", "+verts[3*j+2]);
}
}
};
subObjArray.push(subObj);
}
for(i = 0; i < subObjArray.length; i ++)
{
var currObj = subObjArray[i];
var subGui = gui.addFolder(currObj['name']);
subGui.add(currObj, 'numVertices');
subGui.add(currObj, "ShowCoord");
}
I now have the correct currObj['name'] and currObj['numVertices'] displayed. But all the "ShowCoord" button only contains information of the very last subObj (so console.log("i is " + subObj['index']) will print out 148 every time even if I click different button). How can I make it work? Thanks a lot!
Try moving subGui outside the for loop and modifiy you code so that you don't reassign subGui varialbe.
var subGui = new dat.GUI();
for(i = 0; i < subObjArray.length; i ++)
{
var currObj = subObjArray[i];
subGui.addFolder(currObj['name']);// <--- work on this line
subGui.add(currObj, 'numVertices');
subGui.add(currObj, "ShowCoord");
}
Otherwise it will always be redefined with the last iterated element of for loop
Note: This is just a hint, I can't conclude more from your code.

Categories

Resources