Вызов конструктора, чтобы повторно инициализировать объект

действительно ли возможно повторно инициализировать объект класса с помощью его конструктора?

61
задан cpx 29 January 2010 в 23:53
поделиться

8 ответов

Вроде. Учитывая класс A:

A a;
...
a = A();   

Последнее утверждение не является инициацией, это присвоение, но он, вероятно, делает то, что вы хотите.

76
ответ дан 24 November 2019 в 16:59
поделиться

Почему бы не выполнить только один запрос?

SELECT customer_id, count(*) AS count_all FROM `email_campaign_report_opens` GROUP BY customer_id;

Если у вас так много записей, что вы беспокоитесь о том, чтобы вернуть их все, то делайте это партиями, но я просто не понимаю, почему вы действительно хотите выполнить этот запрос для каждого клиента.

-121--5044587-

Неустранимые исключения, такие как StackOverflowException, обычно приводят к записи в журнале событий Windows (возможно, даже включая трассировку стека). Вы можете отслеживать журнал событий (например, с помощью другой службы), который отправит сообщение электронной почты по определенным записям. Простое приложение для мониторинга записей журнала событий описано здесь:

Средство мониторинга журнала событий в реальном времени

и здесь:

Отправка оповещений по электронной почте при записи ошибок в журнал событий

Если вы хотите, чтобы ваша служба постоянно работала, вы можете настроить ее на автоматический перезапуск в случае сбоя (хотя вы должны знать, что обычно это причина, почему он потерпел крушение и просто перезапуск не обязательно удаляет эту причину). Это можно сделать на вкладке Восстановление в свойствах сервиса. Там также можно вызвать пользовательскую программу или сценарий в случае сбоя службы.

Другой вариант использования встроенных функций Windows - настройка журнала событий для отправки уведомления по электронной почте. Это работает, по крайней мере, из Windows Vista на, как описано здесь:

Как настроить средство просмотра событий, чтобы отправить уведомление по электронной почте в Vista

-121--4998312-

Может быть не то, что вы имеете в виду, но так как вы не упомянули, что это для, я полагаю, один ответ, что вы бы сделать это, контролируя область и поток программы.

Например, вы бы не стали писать такую игру:

initialize player
code for level 1
...
reinitialize player
code for level 2
...
etc

Вместо этого вы бы стремились:

void play_level(level_number, level_data) {
    Player player; //gets "re-initialized" at the beginning of each level using constructor
    //code for level
}

void game() {
    level_number = 1;
    while (some_condition) {
        play_level(level_number, level_data);
        ++level_number;
    }
 }

(Очень грубый набросок, чтобы передать идею, не предназначенную для удаленной компиляции)

2
ответ дан 24 November 2019 в 16:59
поделиться
s/ /\\ /2g

В 2 указывается, что должен применяться второй, а в g указывается, что должны применяться и все остальные. (Вероятно, это работает только на GNU sed. Согласно базовой спецификации Open Group Base Specification, " Если указаны как g , так и n , результаты не указаны. ")

-121--2948923-

Использовать Суп . Используйте lxml . Не используйте регулярные выражения для анализа HTML.


Изменить 2010-01-29: Это было бы разумной отправной точкой для lxml:

from lxml.html import fromstring
from lxml.html.clean import Cleaner
import requests

url = "https://stackoverflow.com/questions/2165943/removing-html-tags-from-a-text-using-regular-expression-in-python"
html = requests.get(url).text

doc = fromstring(html)

tags = ['h1','h2','h3','h4','h5','h6',
       'div', 'span', 
       'img', 'area', 'map']
args = {'meta':False, 'safe_attrs_only':False, 'page_structure':False, 
       'scripts':True, 'style':True, 'links':True, 'remove_tags':tags}
cleaner = Cleaner(**args)

path = '/html/body'
body = doc.xpath(path)[0]

print cleaner.clean_html(body).text_content().encode('ascii', 'ignore')

Вы хотите содержание, так что, вероятно, вы не хотите javascript или CSS. Кроме того, предположительно вы хотите только содержимое в теле, а не HTML из головы, тоже. Прочитайте lxml.html.clean , чтобы узнать, что можно легко удалить. Гораздо умнее регулярных выражений, нет?

Также следите за проблемами кодирования Юникода. Вы можете легко закончить с HTML, который вы не можете напечатать.


2012-11-08: изменено с использования urllib2 на запросы . Просто используйте запросы!

-121--4222943-

Это возможно, хотя это очень плохая идея. Причина в том, что без вызова деструкторов на существующем объекте, вы собираетесь утечку ресурсов.

С этой важной оговоркой, если вы настаиваете на этом, вы можете использовать новое размещение.

// Construct the class
CLASS cl(args);

// And reconstruct it...
new (&cl) CLASS(args);
28
ответ дан 24 November 2019 в 16:59
поделиться

буквально? Да, используя размещение нового. Но сначала вы должны разрушить ранее построенный объект.

SomeClass object(1, 2, 3);
...
object.~SomeClass(); // destruct
new(&object) SomeClass(4, 5, 6); // reconstruct
...
// Final destruction will be done implicitly

Значение этого не выходит за рамки чисто теоретического. Не делай это на практике. Все это уродливо за пределы описания.

49
ответ дан 24 November 2019 в 16:59
поделиться

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

Редактировать

Я не буду признать размещение нового, потому что я не хочу получить домашнее животное для работы.

Видите эту комикс , но подумайте о теме под рукой ...

11
ответ дан 24 November 2019 в 16:59
поделиться

Краткий ответ:

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

class C1 {
public:
  C1(int p1, int p2) {
    Init(p1,p2);
  }
  void Init(int p1, int p2) { ... }
};

Угол NitPicker:

Есть ли немного невероятно злой способ назвать конструктором в C ++ после создания объекта? Почти наверняка, это C ++ в конце концов. Но это принципиально зло, и это поведение почти наверняка не определяется стандартом и следует избегать.

10
ответ дан 24 November 2019 в 16:59
поделиться

Вместо того, чтобы разрушительные и ринитилизовать, как предложено некоторые из ответов выше, лучше сделать назначение, как ниже. Код ниже является безопасным исключением.

    T& reinitialize(int x, int y)
    {
        T other(x, y);
        Swap(other); // this can't throw.
        return *this;
    }
2
ответ дан 24 November 2019 в 16:59
поделиться

Да, вы можете обмануть и использовать размещение нового.
Примечание: я не советую это:

#include <new>

reInitAnA(A& value)
{
    value.~A();            // destroy the old one first.
    new (&value) A();      // Call the constructor 
                           // uses placement new to construct the new object
                           // in the old values location.
}
7
ответ дан 24 November 2019 в 16:59
поделиться
Другие вопросы по тегам:

Похожие вопросы: