AUTOMATIC1111/stable-diffusion-webui · error · Exception

Invalid learning rate schedule. It should be a number or, fo

Error message

Invalid learning rate schedule. It should be a number or, for example, like "0.001:100, 0.00001:1000, 1e-5:10000" to have lr of 0.001 until step 100, 0.00001 until 1000, and 1e-5 until 10000.

What it means

LearnScheduleParser in textual_inversion training parses the learning-rate schedule string. Accepted forms are a single number ('0.001') or comma-separated 'rate:step' pairs ('0.001:100, 0.00001:1000'). Any token that float() cannot parse, or a schedule yielding no rates at all, raises ValueError/AssertionError which is re-raised with this explanatory message.

Source

Thrown at modules/textual_inversion/learn_schedule.py:36

                tmp = pair.split(':')
                if len(tmp) == 2:
                    step = int(tmp[1])
                    if step > cur_step:
                        self.rates.append((float(tmp[0]), min(step, max_steps)))
                        self.maxit += 1
                        if step > max_steps:
                            return
                    elif step == -1:
                        self.rates.append((float(tmp[0]), max_steps))
                        self.maxit += 1
                        return
                else:
                    self.rates.append((float(tmp[0]), max_steps))
                    self.maxit += 1
                    return
            assert self.rates
        except (ValueError, AssertionError) as e:
            raise Exception('Invalid learning rate schedule. It should be a number or, for example, like "0.001:100, 0.00001:1000, 1e-5:10000" to have lr of 0.001 until step 100, 0.00001 until 1000, and 1e-5 until 10000.') from e


    def __iter__(self):
        return self

    def __next__(self):
        if self.it < self.maxit:
            self.it += 1
            return self.rates[self.it - 1]
        else:
            raise StopIteration


class LearnRateScheduler:
    def __init__(self, learn_rate, max_steps, cur_step=0, verbose=True):
        self.schedules = LearnScheduleIterator(learn_rate, max_steps, cur_step)
        (self.learn_rate,  self.end_step) = next(self.schedules)
        self.verbose = verbose

View on GitHub (pinned to 82a973c043)

Solutions

  1. Use a plain float (e.g. 0.001) if you do not need step-based decay
  2. Format the schedule exactly as 'rate:steps, rate:steps' with dot decimals and ASCII colons/commas
  3. Remove trailing/leading commas and verify each rate parses with float() before starting training

Example fix

# before
schedule = '0.001:100, 0,00001:1000'
# after
schedule = '0.001:100, 0.00001:1000'
Defensive patterns

Strategy: validation

Validate before calling

def parse_schedule_ok(schedule: str) -> bool:
    schedule = schedule.strip()
    if not schedule:
        return False
    try:
        for token in schedule.split(','):
            parts = [p.strip() for p in token.split(':')]
            if len(parts) not in (1, 2):
                return False
            float(parts[0])
            if len(parts) == 2:
                int(parts[1])
        return True
    except ValueError:
        return False

Prevention

When it happens

Trigger: Entering a schedule like '0.001:100,abc:200', 'lr:100', an empty string, or trailing commas in the textual-inversion/embedding trainer's Learning rate field; values with spaces inside a token such as '0.001 :100' can also fail float().

Common situations: Typos in the training tab; pasting a schedule from a tutorial that used a different format; localized keyboards inserting non-breaking spaces or comma decimal separators (0,001).

Related errors


AI-assisted analysis of AUTOMATIC1111/stable-diffusion-webui@82a973c043 (2026-08-14). Data as JSON: /api/errors/e8296e8d8e25c9c7. Report an issue: GitHub.