Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1vXk85-003w1f-2P for pgsql-hackers@arkaria.postgresql.org; Mon, 22 Dec 2025 17:55:34 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.96) (envelope-from ) id 1vXk84-00Fi25-03 for pgsql-hackers@arkaria.postgresql.org; Mon, 22 Dec 2025 17:55:32 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1vXk83-00Fi1w-2D for pgsql-hackers@lists.postgresql.org; Mon, 22 Dec 2025 17:55:32 +0000 Received: from mail-lf1-x129.google.com ([2a00:1450:4864:20::129]) by magus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 (Exim 4.96) (envelope-from ) id 1vXk82-0029t3-02 for pgsql-hackers@postgresql.org; Mon, 22 Dec 2025 17:55:32 +0000 Received: by mail-lf1-x129.google.com with SMTP id 2adb3069b0e04-59445ee9738so3243089e87.3 for ; Mon, 22 Dec 2025 09:55:29 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1766426129; x=1767030929; darn=postgresql.org; h=content-transfer-encoding:in-reply-to:from:content-language :references:cc:to:subject:user-agent:mime-version:date:message-id :from:to:cc:subject:date:message-id:reply-to; bh=oXpv405b8wLQW3KWphSzp5ue7w6VavXqIgrANpSzjuk=; b=EeX1l0XnbRgbzSPtchCGTRYDqgFL98jPeGymt43xE5DhIY8Dz5uMMEEWxDIdnOxg6P tR7a80jpD8+eFFeMb9TpiptfBujV99Hwd4gbMYZKkkLZ6KvvKqFkJsw9/rdsCg2K6xO5 XZBxY/hYmwvLwTgSac4fu/1OU28dydemW2eRIVSWgxt7uQMfiPj1992OAA+T4/5F40RM 7H4FN6lvk4hxEcJmtgRDyoFfm11lum9ICTbA09kTxTpT1DQB/Rt3BVVFTmQKgx4hwkqY Cm0YMLNCuyKAwv3kp6hCU6e/vM2Jgkfz5zsViHD6cMbj1MSlumIaH4HHABPDSHep96ah 2KAA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1766426129; x=1767030929; h=content-transfer-encoding:in-reply-to:from:content-language :references:cc:to:subject:user-agent:mime-version:date:message-id :x-gm-gg:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=oXpv405b8wLQW3KWphSzp5ue7w6VavXqIgrANpSzjuk=; b=KR/uRdEck4H93uPPVLSrE5LU6MFgJseyAg5ESyTLUYpBLBrfPJfM5EiteqTUM2q6Km aQWBL1niPRJ0VfG0POBGmK/VDtWzk97sCid3aXYGZxmkBS38JmMcAosYKPl2yboYTR/Z EkGNGdueygsm3cFiKt7VdkUI5n61A1o8LR4dDkZ1nrWWI7stflKRX9Ij+p8xjJ67w+6q G5XMyN/+fLBqfGXjPInxMmlqe+INJGY7BBhRrmEwnL/55JQwCxBOKJixG21b6+o3rfy7 Jh4cP3z01vLt7yEdg13XRrkbvsyswzzU5t5f3eINqIEKQimyWPMj+aOyEsiCC01EqNwQ f2Ug== X-Forwarded-Encrypted: i=1; AJvYcCWCCwOgvi2IUDyx9GvPKEATjDQfFfoHuklgROueQk1fOs4bUlVXFIvpga35LwCNDPSK98lA/5ZZtxhD1LtG@postgresql.org X-Gm-Message-State: AOJu0YwZdC1THQMtoeB4KarM4CSBfmcyY0/7BlZfQ78OEJ1y+L0YQEAy 4w7SSlFljxJ4QqHH3tNQdJ2lrESToRJ8WLYRPHq0L3HaFXV25bUKkDxW X-Gm-Gg: AY/fxX5+hl8X+0C7pDNo6iEKatt57tgog4W+yYVBvc24qHqnQfN194GyLKvYpggn7lh J/dlTHoVZW6m2FTtgVDG0mzRRvM6cgMo8ITrUl/BrpagS9jkiwzF220hChvL6c9sB6QYobAV+Sd DRhj6ZAUpfItybq86FZfbW0F8C63N2MmEjkJoQJzB+lmfs0Baye6pcrP4uflPoSHFrCz1OHOsN9 SHjYpaDcCBtw6rLoktdjzQnDdq1hvl1YQaOUpUSJG9jUaUvITGDZagFIsSFbb4tlal9ZHjZQKz2 wkcOU6yDSV2LJ5pR8WBFPJIdzgX2/CCqMdQmlkatwH6WlWFrJDEhGGRjPn5ekumrN5FxyYY7m+5 JZmplX3lQ4HXNJMyNzcTv7ne84G0fPrM2lcDCzmbQhmRl363wzf6tJ+9x1u6J2LBfg/CQqW0kYW sBvybdfqNXwTk0xYf2jlLd1lTHgvNDxMpa5C4cNuCukcxZYCgc+mNluJWcs3GrV530ddVQMXCk X-Google-Smtp-Source: AGHT+IE68otEEKi/jZxKo1GnoH4vqI4WXOQkK2zMkXHl4cqGBOqujfPjrf4G/N19N5Q9KtiPSai6hw== X-Received: by 2002:a05:6512:2353:b0:591:c3f1:474d with SMTP id 2adb3069b0e04-59a17d239demr4095268e87.15.1766426128773; Mon, 22 Dec 2025 09:55:28 -0800 (PST) Received: from [192.168.50.127] (broadband-90-154-71-126.ip.moscow.rt.ru. [90.154.71.126]) by smtp.gmail.com with ESMTPSA id 2adb3069b0e04-59a185ddad3sm3353768e87.32.2025.12.22.09.55.28 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Mon, 22 Dec 2025 09:55:28 -0800 (PST) Message-ID: <7b76973b-e9b6-4f80-a1d2-4bd467e38346@gmail.com> Date: Mon, 22 Dec 2025 20:55:28 +0300 MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: Re: Improve the performance of Unicode Normalization Forms. To: Heikki Linnakangas Cc: Jeff Davis , PostgreSQL Hackers References: <844d3dd7-2955-4794-95d1-7f4c13cb89fc@gmail.com> <96c54fc3dde2ebaccafbd1ffa29b8be1005c8b8c.camel@j-davis.com> <677cde50-6d64-474b-9ba8-bab380a111b3@gmail.com> <599663a8d5948243bd87bf55a4f76bbb4a51a6e8.camel@j-davis.com> <85f2a36f-f70a-4667-be48-49b652457295@gmail.com> <088432f3-a3a9-4c40-8295-6c687c25d651@gmail.com> <1260f607-8d90-4cf2-accc-45aa6eab63d8@gmail.com> <7859e5ef-a574-4199-a69b-6fee26711521@gmail.com> <11f371fe-9c97-4c71-957a-a4cd3813cc55@gmail.com> <5f8639d99dab0d95dc1ef8f3abd4aa3adc0332ee.camel@j-davis.com> <58c6cea8-a5b1-4a8a-8044-18ef0011a168@gmail.com> Content-Language: ru From: Alexander Borisov In-Reply-To: Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk 22.12.2025 19:24, Heikki Linnakangas wrote: > On 22/12/2025 17:44, Alexander Borisov wrote: >> The branching kept bothering me. The algorithm consisted of a function >> with branches (essentially a binary search with offsets) and a table of >> indexes. I really wanted to get rid of the branches. And then it dawned >> on me that instead of building branches with offsets, I could create >> another table that would contain these offsets. >> The "inspiration" came from my patch Optimization of the is_normalized() >> function [0]. >> >> Actually, I changed the GenerateSparseArray algorithm, which now >> generates a table with offsets instead of a function with branches. >> In other words, we now have two tables: >> 1. A table with offsets, indicating what offset is needed to obtain the >>     desired index from the index table. >> 2. A table with indexes. The data is divided into fixed ranges. > > Sounds like you re-invented the radix tree :-). Nothing wrong with that; > a radix tree sounds like a good data structure for this. I looked at the implementation of radix trees for Encoding in PostgreSQL. There are similarities, of course, but in my implementation, the access speed is literally O(1). For example: return table_index[ table_offset[cp >> 6] + (cp & 63) ]; Access speed in Encoding (radix tree), it is more complicated. If I understand correctly. In general, there was an idea to store offset and index data in one table. Not to separate them. But I'm sure you'll understand everything when you see the code. >>  > The GenerateSparseArray adds comments like "/* U+1234 */" to each >>  > element. That's nice but it implies that the elements are unicode code >>  > points. GenerateSparseArray could be used for many other things. Let's >>  > use "/* 0x1234 */" instead, or make it somehow configurable. >>  > >>  > The generated file is very large, over 1 MB. I guess it doesn't matter >>  > all that much, but perhaps we should generate a little more compact >>  > code. Maybe we don't need the "/* U+1234 */" comment on every line, >> but >>  > only one comment for each range, for example. >> >> I have many places where I need to generate C tables. To make my life >> easier, and perhaps the lives of others, I added a small module for >> generating "pretty" tables. ./src/tools/PrettyLine.pm >> After applying it, the size of the generated header file was reduced >> to ~300KB. > > I think a fixed number of values per line would look nicer than trying > to pack as much possible on each line. > > (This isn't too important of course, this is just about making the > generated code look prettier.) With a sense of inner beauty :), when the number of values in a line is fixed, the lines start to "dance", which doesn't look very good. On the other hand, we can convert all values to %06X or something like that. But then it would defeat the whole purpose of the idea — to reduce the file size and make it look nice. I use this approach to create many tables, which allows me not to think about how the numbers will fit in and not waste time on it. But, it's more a matter of taste. > Thanks, I'll try to find time to take a closer look. Thank you for your time. -- Regards, Alexander Borisov