LINUX.ORG.RU

[js] Что делать, чтобы не было путаницы с this в роли контекста и в роли создаваемого объекта?

 


0

2

А то получается, что в некоторых методах нужно, чтобы this указывало на объект, а оно указывает на всякий мусор.

★★★★★

Последнее исправление: sphericalhorse (всего исправлений: 1)

Ответ на: комментарий от trashymichael

bind гуглить, или это фича из coffee?
А так, несмотря на ярую любовью к jade и stylus, я против этого вашего coffee — слишком уж высокоуровнев сабж, хотя идея хороша, от скобок бы отказался.

sphericalhorse ★★★★★
() автор топика

enjoy your f%cking javascript.
Сам сижу сейчас разбираюсь в этом говноязычке. Ничего более убогого я не видел. Даже питон выглядит получше.

JFreeM ★★★☆
()
new (function() {
  this.message = "ok";
  var thiz = this;
  window.onload = function() {
    alert(thiz.message);
  }

})();

belous_k_a
()
Ответ на: комментарий от sphericalhorse

имеется в виду конструкция
that = this, т.е. внутри класса создается поле инстанса что ли. Как-то так.

JFreeM ★★★☆
()
Ответ на: комментарий от sphericalhorse

См. ниже :} Хотя я продпочитаю название self.

Deleted
()
Ответ на: комментарий от sphericalhorse

не знаю как где, вроде собирались запилить, у меня лично в рамках undersore в данный момент (underscore.js)

trashymichael ★★★
()
Ответ на: комментарий от sphericalhorse

s/дочернем класе/дочернем конструкторе/

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

Язык прекрасен.

Милейший, вы искренни?

var i = new (function(){
  this.publicVaribale = 0;
  var privateVaribale = 1;
  globalVaribale = 2; // suprise?  hahaha!
})();

Учтите еще необходимость всегда обращаться к переменным-членам объекта через this - это те самые вкусные иголочки сего кактуса которые протыкают сейчас вам небо и заставили создать сию тему.

belous_k_a
()
Ответ на: комментарий от Deleted

Блин, у меня просто 500 строк кода и я уже не всё помню.

Подождите несколько минут. Сейчас рожу.

sphericalhorse ★★★★★
() автор топика

Кстати о прекрасности языка. Погугли на тему «use strict» javascript. В браузерах это не работает, но проблемы покажет.

Deleted
()
Ответ на: комментарий от sphericalhorse

Что не так?

Милейший, если вы не видите аморальные относительно здравого смысла способы указания области видимости, то садик лопнет.

belous_k_a
()
Ответ на: комментарий от Deleted
[ivan@arch tmp]$ cat this.js 
function a() {
	this.head = {}
	var opt = function () {
		console.log(this === global) // true
		console.log(this.head.ass) // cannot read prop...
	}
	this.show = function () {
		opt()
	}
}

function b() {
  this.head.ass = 'not head'
}
b.prototype = new a()

obj = new b()
obj.show()



[ivan@arch tmp]$ cat self.js 
function __spFormMethods() {
	var self = this
	self.formAttrs // <form> tag attrbutes
	self.form = {} // Result

	self.addInput = function () {
		var field = document.createElement('input') 

		self.form.appendChild(field)// Object #<Object> has no method 'appendChild'
	}
}

function spForm() {
	var self = this
	self.form = document.createElement('form')
}
spForm.prototype = new __spFormMethods()


var test = new spForm()
test.addInput()

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

Хотя в варианте с self получается, что метод из родительского класса не имеет доступа к свойствам дочернего.

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

Оно? Если я правильно понимаю, что ты хочешь. Терпеть не могу прототипы, так что могу и наврать :}

function __spFormMethods() {
	this.self = this;
	//self.formAttrs // <form> tag attrbutes
	self.form = {}; // Result

	self.addInput = function () {
		var field = document.createElement('input');
		self.form.appendChild(field); // Object #<Object> has no method 'appendChild'
	}
	return self
}

function spForm() {
	self.form = document.createElement('form');
}

spForm.prototype = new __spFormMethods();
var test = new spForm();
test.addInput();
Deleted
()
Ответ на: комментарий от xpahos

Мои знания скудны, но мне кажется, что это конструктор.

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от Deleted

Ещё один завтык с моей стороны. В браузере self - глобальная переменная. Меняем self на that и код не работает.

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от Deleted

Что тогда делать? Нужна куча объектов, в которых методы и некоторые свойства совпадают. Раньше всё работало впихивая все методы в каждый объект, но это было до того, как всё в гитхаб попало.

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

Я так понимаю, переходить на процедурный стиль уже поздно? Забить и пользоваться this :}

Ну, может завтра ещё JFreeM напишет что.

Deleted
()

используйте coffee-script на мой взгляд вторая из двух главных его фич (первая это невозможность засорить глобальный скоп). http://coffeescript.org/#fat_arrow

special-k ★★★★
()
Ответ на: комментарий от Deleted

Я так понимаю, переходить на процедурный стиль уже поздно?

Я матана не знаю. Пример этого вашего процедурного стиля можно?

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

tl;dr Процедурный — функциями, без объектов.

Deleted
()
Ответ на: комментарий от sphericalhorse
function a() {
	this.head = {};
}
a.prototype.show = function() {
   print(this.head.ass);
};
b.prototype = new a();
function b() {
  this.head.ass = 'not head'; 
}
obj = new b()
obj.show();

d8> load(«this.js»)
not head

Как-то так

d0cent
()
Ответ на: комментарий от sphericalhorse

попробуй кофе, серьезно, там ничего такого нет, документация на одной страничке. сам пару дней назад начал и очень доволен, не пожалел.

trashymichael ★★★
()
Ответ на: комментарий от sphericalhorse

натупил. ты просто запутался уже совсем, короче суть такова (псевдокод)

var __spFormMethods = function () {

}

__spFormMethods.prototype = new Object()

__spFormMethods.prototype.addInput = function () {
  var field = document.createElement("input")
  this.form.appendChild(field)
}

var spForm = function () {
  __spFormMethods.apply(this, [])
  this.form = document.createElement("form")
}

spForm.prototype = new __spFormMethods()
trashymichael ★★★
()
Ответ на: комментарий от sphericalhorse

Не, я JS использую лишь на уровне «постольку поскольку». А this пользуюсь крайне редко (использую лишь как «быструю» ссылку на объект псевдокласса в «конструкторе»).

Eddy_Em ☆☆☆☆☆
()

в js принято писать var that/self = this;

grouzen ★★
()
Ответ на: комментарий от belous_k_a

globalVaribale = 2; // suprise? hahaha!

Сюрприз только для невежды. :)

Reaper ★★
()

Что делать, чтобы не было путаницы с this

Выучить, куда указывает this?

1) Если функция вызывается через new как конструктор объекта, this указывает на создаваемый объект.
2) Если функция запущена как метод объекта, this будет ссылкой на этот объект.
3) Если функция вызывается через call или apply, this указывает на объект переданный в call / apply.
4) В просто вызове функции, this становится равным глобальному объекту.

Reaper ★★
()

To special-k, trashymichael: вот вам сервер-обработчик coffee (а за одно и Jade + Stylus): https://github.com/sphericalhorse/tplhandler

How to
1. Запускаете сервер.
2. Кладете в папочку public ваши coffee-файлы, и гипертекст, в котором их подключаете, например так:

<script src="test.js"></script>
Тогда обработается и отправиться файл ./public/test.coffee.
3. Profit!

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

То, что ты пытался сделать:

function Base() {
 this.head = {};
 var self = this;
 var bar = function () {
  console.log(self); 
  console.log(self.head.ass);
 }
 this.foo = function () { bar(); }
}

function Derived() {
  this.head.ass = 'not head';
}
Derived.prototype = new Base;

var obj = new Derived;
obj.foo();

Проблема твоего кода в том, что ты внутри функции opt обращаешься к this... который указывает на глобальный объект, а не на то что тебе нужно, т.е. на b.prototype:

function a() {
	this.head = {}
	var opt = function () {
		console.log(this === global) // true
		console.log(this.head.ass) // cannot read prop...
	}
	this.show = function () {
		opt()
	}
}

function b() {
  this.head.ass = 'not head'
}
b.prototype = new a()

obj = new b()
obj.show()

Т.е. внутри ф-ии a() this указывает туда, куда ты предполагаешь, но внутри a.opt() уже в другое место.

Reaper ★★
()
Ответ на: комментарий от sphericalhorse

1) кофе можно на клиенте обрабатывать, насколько я помню 2) я предпочитаю компилировать, сразу ошибки всплывают, например, кроме того часто много чего компилировать надо внагрузку, меня не напрягает, да и ватчей можно навешать если надо

trashymichael ★★★
()
Ответ на: комментарий от trashymichael

Если при конпелции всплывают ошибки, то сервер пишет.

sphericalhorse ★★★★★
() автор топика

Надеюсь, последний вопрос:

function p () {
  this.show = function () {
    cnosole.log(e)
  }
}
function c () {
  var e = 'asd'
}
c.prototype = new p()

var k = new c()

k.show()

Тут можно что-то сделать?

ПС: кофе посмотрел и отложил на будущее. Сначала необходимо весь этот прототипный матан выучить.

sphericalhorse ★★★★★
() автор топика
Ответ на: комментарий от sphericalhorse

короче бесплатный хинт: всегда объявляй функции через var bla = function а не как ты делашь (не спрашивай зачем — гугли)

далее, методы надо объявлять впрототипе, как я выше писал, в конструкторе надо только их вызывать и устанавливать данные, например. иначе методы будут объявляться каждый раз при new, это же очевидно. конструктор это просто функция конструктор а не декларация класса

короче

var p = function () { }

p.prototype = new Object()

p.prototype.show = function () { console.log(this.e) }

var c = function () {
p.apply(this, [])
this.e = "asd"
}

c.prototype = new p()

k = new c() k.show()
trashymichael ★★★
()
Ответ на: комментарий от sphericalhorse
par = new () ->
	e = 10
	this.gett = () ->
		console.log e
		return

	this.child = () ->
		this.showe = () ->
			alert e
			return
		return
	this.child.prototype = this

	return

child = par.child

item = new child()
sphericalhorse ★★★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.