├── docs
├── Programming-is-Writing-is-Programming.pdf
├── NIPS-2017-attention-is-all-you-need-Paper.pdf
├── No Silver Bullet - Fred Brooks in (1986)
│ └── README.md
└── No Silver Bullet - Fred Brooks in (1986)[KOR]
│ └── README.md
├── .gitignore
└── README.md
/docs/Programming-is-Writing-is-Programming.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jujumilk3/to-become-a-better-programmer/HEAD/docs/Programming-is-Writing-is-Programming.pdf
--------------------------------------------------------------------------------
/docs/NIPS-2017-attention-is-all-you-need-Paper.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/jujumilk3/to-become-a-better-programmer/HEAD/docs/NIPS-2017-attention-is-all-you-need-Paper.pdf
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Created by .ignore support plugin (hsz.mobi)
2 | ### Example user template template
3 | ### Example user template
4 |
5 | # IntelliJ project files
6 | .idea
7 | out
8 | gen
9 | .history
10 | .vscode
11 |
--------------------------------------------------------------------------------
/docs/No Silver Bullet - Fred Brooks in (1986)/README.md:
--------------------------------------------------------------------------------
1 | # No Silver Bullet —Essence and Accident in Software Engineering
2 |
3 | Frederick P. Brooks, Jr.
4 | University of North Carolina at Chapel Hill
5 |
6 | > There is no single development, in either technology or management technique,
7 | which by itself promises even one order-of-magnitude improvement within a decade in productivity,
8 | in reliability, in simplicity.
9 |
10 |
11 | ## Abstract1
12 | All software construction involves essential tasks,
13 | the fashioning of the complex conceptual structures that composethe abstract software entity,
14 | and accidental tasks, the representation of these abstract entities in programming languages
15 | and the mapping of these onto machine languages within space and speed constraints.
16 | Most of the big past gains in software productivity have come from removing artificial
17 | barriers that have made the accidental tasks inordinately hard,
18 | such as severe hardware constraints, awkward programming languages,
19 | lack of machine time. How much of what software engineers now do is
20 | still devoted to the accidental, as opposed to the essential?
21 | Unless it is more than 9/10 of all effort, shrinking all the accidental activities
22 | to zero time will not give an order of magnitude improvement.
23 |
24 | Therefore it appears that the time has come to address
25 | the essential parts of the software task,
26 | those concerned with fashioning abstract conceptual structures of great complexity.
27 | I suggest:
28 | - Exploiting the mass market to avoid constructing what can be bought.
29 | - Using rapid prototyping as part of a planned iteration in establishing software requirements.
30 | - Growing software organically, adding more and more function to systems as they are run, used, and tested.
31 | - Identifying and developing the great conceptual designers of the rising generation.
32 |
33 |
34 | ## Introduction
35 | Of all the monsters who fill the nightmares of our folklore,
36 | none terrify more than werewolves, because they transform unexpectedly
37 | from the familiar into horrors. For these, we seek bullets of silver
38 | than can magically lay them to rest.
39 |
40 | The familiar software project has something of this character
41 | (at least as seen by the non-technical manager),
42 | usually innocent and straightforward,
43 | but capable of becoming a monster of missed schedules, blown budgets,
44 | and flawed products. So we hear desperate cries for a silver bullet,
45 | something to make software costs drop as rapidly as computer hardware costs do.
46 |
47 | But, as we look to the horizon of a decade hence,
48 | we see no silver bullet. There is no single development,
49 | in either technology or management technique,
50 | which by itself promises even one order of magnitude improvement in productivity,
51 | in reliability, in simplicity. In this chapter we shall try to see why,
52 | but examining both the nature of the software problem and the properties of
53 | the bullets proposed.
54 |
55 | Skepticism is not pessimism, however.
56 | Although we see no startling breakthroughs,
57 | and indeed, believe such to be inconsistent with the nature of software,
58 | many encouraging innovations are under way.
59 | A disciplined, consistent effort to develop, propagate,
60 | and exploit them should indeed yield an order-of-magnitude improvement.
61 | There is no royal road, but there is a road.
62 |
63 | The first step toward the management of disease was replacement of
64 | demon theories and humours theories by the germ theory.
65 | That very step, the beginning of hope, in itself dashed all hopes of magical solutions.
66 | It told workers the progress would be made stepwise, at great effort,
67 | and that a persistent, unremitting care would have to be paid to a discipline of
68 | cleanliness. So it is with software engineering today.
69 |
70 |
71 |
72 | ## Does It Have To Be Hard? – Essential Difficulties
73 | Not only are there no silver bullets now in view, the very nature of software makes it unlikely that there will be any−no inventions that will do for software productivity, reliability, and simplicity what electronics, transistors, and large-scale integration did for computer hardware. We cannot expect ever to see twofold gains every two years.
74 |
75 | First, we must observe that the anomaly is not that software progress is so slow but that computer hardware progress is so fast. No other technology since civilization began has seen six orders of magnitude price-performance gain in 30 years. In no other technology can one choose to take the gain in either improved performance or in reduced costs. These gains flow from the transformation of computer manufacture from an assembly industry into a process industry.
76 |
77 | Second, to see what rate of progress we can expect in software technology, let us examine its difficulties. Following Aristotle, I divide them into essence−the difficulties inherent in the nature of the software−and accidents−those difficulties that today attend its production but that are not inherent.
78 |
79 | The accidents I discuss in the next section. First let us consider the essence.
80 |
81 | The essence of a software entity is a construct of interlocking concepts: data sets, relationships among data items, algorithms, and invocations of functions. This essence is abstract, in that the conceptual construct is the same under many different representations. It is nonetheless highly precise and richly detailed.
82 |
83 | I believe the hard part of building software to be the specification, design, and testing of this conceptual construct, not the labor of representing it and testing the fidelity of the representation. We still make syntax errors, to be sure; but they are fuzz compared to the conceptual errors in most systems.
84 |
85 | If this is true, building software will always be hard. There is inherently no silver bullet.
86 |
87 | Let us consider the inherent properties of this irreducible essence of modern software systems: complexity, conformity, changeability, and invisibility.
88 |
89 | **Complexity.** Software entities are more complex for their size than perhaps any other human construct, because no two parts are alike (at least above the statement level). If they are, we make the two similar parts into one, a subroutine, open or closed. In this respect software systems differ profoundly from computers, buildings, or automobiles, where repeated elements abound.
90 |
91 | Digital computers are themselves more complex than most things people build; they have very large numbers of states. This makes conceiving, describing, and testing them hard. Software systems have orders of magnitude more states than computers do.
92 |
93 | Likewise, a scaling-up of a software entity is not merely a repetition of the same elements in larger size; it is necessarily an increase in the number of different elements. In most cases, the elements interact with each other in some nonlinear fashion, and the complexity of the whole increases much more than linearly.
94 |
95 | The complexity of software is in essential property, not an accidental one. Hence descriptions of a software entity that abstract away its complexity often abstract away its essence. Mathematics and the physical sciences made great strides for three centuries by constructing simplified models of complex phenomena, deriving properties from the models, and verifying those properties experimentally. This worked because the complexities ignored in the models were not the essential properties of the phenomena. It does not work when the complexities are the essence.
96 |
97 | Many of the classical problems of developing software products derived from this essential complexity and its nonlinear increased with size. From the complexity comes the difficulty of communication among team members, which leads to product flaws, cost overruns, schedule delays. From the complexity comes the difficulty of enumerating, much less understanding, all the possible states of the program, and from that comes the unreliability. From the complexity of the functions comes the difficulty of invoking those functions, which makes programs hard to use. From complexity of structure comes the difficulty of extending programs to new functions without creating side effects. From the complexity of structure comes the unvisualized state that that constitute security trapdoors.
98 |
99 | Not only technical problems but management problems as well come from the complexity. This complexity makes overview hard, thus impeding conceptual integrity. It makes it hard to find and control all the loose ends. It creates the tremendous learning and understanding burden that makes personnel turnover a disaster.
100 |
101 | **Conformity.** Software people are not alone in facing complexity. Physics deals with terribly complex objects even at the “fundamental” particle level. The physicist labors on, however, in a firm faith that there are unifying principles to be found, whether in quarks or in unified field theories. Einstein repeatedly argued that there must be simplified explanations of nature, because God is not capricious or arbitrary.
102 |
103 | No such faith comforts the software engineer. Much of the complexity he must master is arbitrary complexity, forced without rhyme or reason by the many human institutions and systems to which his interfaces must confirm. These differ from interface to interface, and from time to time, not because of necessity but only because they were designed by different people, rather than by God.
104 |
105 | In many cases the software must confirm because it has most recently come to the scene. In others it must conform because it is perceived as the most conformable. But in all cases, much complexity comes from conformation to other interfaces; this cannot be simplified out by any redesign of the software alone.
106 |
107 | **Changeability.** The software entity is constantly subject to pressures for change. Of course, so are buildings, cars, and computers. But manufactured things are infrequently changed after manufacture; they are superseded by later models, or essential changes are incorporated in later serial-number copies of the same basic design. Callbacks of automobiles are really quite infrequent; field changes of computers somewhat less so. Both are much less frequent than modifications to fielded software.
108 |
109 | Partly this is because the software in a system embodies its function, and the function is the part that most feels the pressures of change. Partly it is because software can be changed more easily−it is pure thought-stuff, infinitely malleable. Buildings do in fact get changed, but the high costs of change, understood by all, serve to dampen the whim of the changers.
110 |
111 | All successful software gets changed. Two processes are at work. As a software product is found to be useful, people try it in new cases at the edge of, or beyond, the original domain. The pressures for extended function come chiefly from users who like the basic function and invent new uses for it.
112 |
113 | Second, successful software also survives beyond the normal life of the machine vehicle for which it is first written. If not new computers, then at least new disks, new displays, new printers come along; and the software must be conformed to its new vehicles of opportunity.
114 |
115 | In short, the software product is embedded in a cultural matrix of applications, users, laws, and machine vehicles. These all change continually, and their changes inexorably force change upon the software product.
116 |
117 | **Invisibility.** Software is invisible and unvisualizable. Geometric abstractions are powerful tools. The floor plan of a building helps both architect and client evaluate spaces, traffic flows, and views. Contradictions become obvious, omissions can be caught. Scale drawings of mechanical parts and stick-figure models of molecules, although abstractions, serve the same purpose. A geometric reality is captured in a geometric abstraction.
118 |
119 | The reality of software is not inherently embedded in space. Hence it has no ready geometric representation in the way that land has maps, silicon chips have diagrams, computers have connectivity schematics. As soon as we attempt to diagram software structure, we find it to constitute not one, but several, general directed graphs, superimposed one upon another. The several graphs may represent the flow of control, the flow of data, patterns of dependency, time sequence, name-space relationships. These are usually not even planar, much less hierarchical. Indeed, one of the ways of establishing conceptual control over such structure is to enforce link cutting until one or more of the graphs becomes hierarchical.2
120 |
121 | In spite of progress in restricting and simplifying the structures of software, they remain inherently unvisualizable, thus depriving the mind of some of its most powerful conceptual tools. This lack not only impedes the process of design within one mind, it severely hinders communication among minds.
122 |
123 |
124 | ## Past Breakthroughs Solved Accidental Difficulties
125 | If we examine the three steps in software technology that have been most fruitful in the past, we discover that each attacked a different major difficulty in building software, but they have been the accidental, not the essential, difficulties. We can also see the natural limits to the extrapolation of each such attack.
126 |
127 | **High-level languages.** Surely the most powerful stroke for software productivity, reliability, and simplicity has been the progressive use of high-level languages for programming. Most observers credit that development with at least a factor of five in productivity, and with concomitant gains in reliability, simplicity, and comprehensibility
128 |
129 | What does a high-level language accomplish? It frees a program from much of its accidental complexity. An abstract program consists of conceptual constructs: operations, data types, sequences, and communication. The concrete machine program is concerned with bits, registers, conditions, branches, channels, disks, and such. To the extent that the high-level language embodies the constructs wanted in the abstract program and avoids all lower ones, it eliminates a whole level of complexity that was never inherent in the program at all.
130 |
131 | The most a high-level language can do is to furnish all the constructs the programmer imagines in the abstract program. To be sure, the level of our sophistication in thinking about data structures, data types, and operations is steadily rising, but at an ever-decreasing rate. And language development approaches closer and closer to the sophistication of users.
132 |
133 | Moreover, at some point the elaboration of a high-level language becomes a burden that increases, not reduces, the intellectual task of the user who rarely uses the esoteric constructs.
134 |
135 | **Time-sharing.** Most observers credit time-sharing with a major improvement in the productivity of programmers and in the quality of their product, although not so large as that brought by high-level languages.
136 |
137 | Time-sharing attacks a distinctly different difficulty. Time-sharing preserves immediacy, and hence enables us to maintain an overview of complexity. The slow turnaround of batch programming means that we inevitably forget the minutiae, if not the very thrust, of what we were thinking when we stopped programming and called for compilation and execution. This interruption of consciousness is costly in time, for we must refresh. The most serious effect may well be the decay of grasp of all that is going on in a complex system.
138 |
139 | Slow turn-around, like machine-language complexities, is an accidental rather than an essential difficulty of the software process. The limits of the contribution of time-sharing derive directly. The principle effect is to shorten system response time. As it goes to zero, at some point it passes the human threshold of noticeability, about 100 milliseconds. Beyond that no benefits are to be expected.
140 |
141 | **Unified programming environments.** Unix and Interlisp, the first integrated programming environments to come into widespread use, are perceived to have improved productivity by integral factors. Why?
142 |
143 | They attack the accidental difficulties of using programs together, by providing integrated libraries, unified file formats, and piles and filters. As a result, conceptual structures that in principle could always call, feed, and use one another can indeed easily do so in practice.
144 |
145 | This breakthrough in turn stimulated the development of whole toolbenches, since each new tool could be applied to any programs by using the standard formats.
146 |
147 | Because of these successes, environments are the subject of much of today’s software engineering research. We will look at their promise and limitations in the next section.
148 |
149 |
150 | ## Hopes for the Silver
151 | Now lets us consider the technical developments that are most often advanced as potential silver bullets. What problems do they address? Are they the problems of essence, or are they remainders of our accidental difficulties? Do they offer revolutionary advances, or incremental ones?
152 |
153 | **Ada and other high-level language advances.** One of the most touted recent developments is the programming language Ada, a general-purpose, high-level language of the 1980s. Ada indeed not only reflects evolutionary improvements in language concepts but embodies features to encourage modern design and modularization concepts. Perhaps the Ada philosophy is more of an advance than the Ada language, for it is the philosophy of modularization, of abstract data types, of hierarchical structuring. Ada is perhaps over-rich, the natural product of the process by which requirements were laid on its design. That is not fatal, for subset working vocabularies can solve the learning problem, and hardware advances will give us the cheap MIPS to pay for the compiling costs. Advancing the structuring of software systems is indeed a very good use for the increased MIPS our dollars will buy. Operating systems, loudly decried in the 1960s for their memory and cycle costs, have proved to be an excellent form in which to use some of the MIPS and cheap memory bytes of the past hardware surge.
154 |
155 | Nevertheless, Ada will not prove to be the silver bullet that slays the software productivity monster. It is, after all, just another high-level language, and the biggest payoff from such languages came from the first transition, up from the accidental complexities of the machine into the more abstract statement of step-by-step solutions. Once those accidents have been removed, the remaining ones are smaller, and the payoff from their removal will surely be less.
156 |
157 | I predict that a decade from now, when the effectiveness of Ada is assessed, it will be seen to have made a substantial difference, but not because of any particular language feature, nor indeed because of all of them combined. Neither will the new Ada environment prove to be the cause of the improvements. Ada’s greatest contribution will be that switching to it occasioned training programmers in modern software design techniques.
158 |
159 | **Object-oriented programming.** Many students of the art hold out more hope for object-oriented programming than for any of the other technical fads of the day.3 I am among them. Mark Sherman of Dartmouth notes that we must be careful to distinguish two separate ideas that go under that name: abstract data types and hierarchical types, also called classes. The concept of the abstract data type is that an object’s type should be defined by a name, a set of proper values, and a set of proper operations, rather than its storage structure, which should be hidden. Examples are Ada packages (with private types) or Modula’s modules.
160 |
161 | Hierarchical types, such as Simula-67’s classes, allow the definition of general interfaces that can be further refined by providing subordinate types. The two concepts are orthogonal−there may be hierarchies without hiding and hiding without hierarchies. Both concepts represent real advances in the art of building software.
162 |
163 | Each removes one more accidental difficulty from the process, allowing the designer to express the essence of his design without having to express large amounts of syntactic material that add no new information content. For both abstract types and hierarchical types, the result is to remove a higher-order sort of accidental difficulty and allow a higher-order expression of design.
164 |
165 | Nevertheless, such advances can do no more than to remove all the accidental difficulties from the expression of the design. The complexity of the design itself is essential; and such attacks make no change whatever in that. An order-of-magnitude gain can be made by object-oriented programming only if the unnecessary underbrush of type specification remaining today in our programming language is itself responsible for nine-tenths of the work involved in designing a program product. I doubt it.
166 |
167 | **Artificial intelligence.** Many people expect advances in artificial intelligence to provide the revolutionary breakthrough that will give order-of-magnitude gains in software productivity and quality.4 I do not. To see why, we must dissect what is meant by “artificial intelligence” and then see how it applies.
168 | >**Parnas has clarified the terminological chaos:**
169 | *Two quite different definitions of AI are in common use today. AI-1: The use of computers to solve problems that previously could only be solved by applying human intelligence. AI-2: The use of a specific set of programming techniques knows as heuristic or rule-based programming. In this approach human experts are studies to determine what heuristics or rules of thumb they use in solving problems... The program is designed to solve a problem the way that humans seem to solve it.
170 | The first definition has a sliding meaning... Something can fit the definition of AI-1 today but, once we see how the program works and understand the problem, we will not think of it as AI anymore... Unfortunately I cannot identify a body of technology that is unique to this field... Most of the work is problem-specific, and some abstraction or creativity is require to see how to transfer it.5*
171 |
172 | I agree completely with this critique. The techniques used for speech recognition seem to have little in common with those used for image recognition, and both are different from those used in expert systems. I have a hard time seeing how image recognition, for example, will make any appreciable difference in programming practice. The same is try of speech recognition. The hard thing about building software is deciding what to say, not saying it. No facilitation of expression can give more than marginal gains.
173 |
174 | Expert systems technology, AI-2, deserves a section of its own.
175 |
176 | **Expert systems.** The most advanced part of the artificial intelligence art, and the most widely applies, is the technology for building expert systems. Many software scientists are hard at work applying this technology to the software-building environment.6 What is the concept, and what are the prospects?
177 |
178 | An expert system is a program containing a generalized inference engine and a rule base, designed to take input data and assumptions and explore the logical consequences through the inferences derivable from the rule base, yielding conclusions and advice, and offering to explain its results by retracing its reasoning for the user. The inference engines typically can deal with fuzzy or probabilistic data and rules in addition to purely deterministic logic.
179 |
180 | Such systems offer some clear advantages over programmed algorithms for arriving at the same solutions to the same problems:
181 | - Inference engine technology is developed in an application-independent way, and then applied to many uses. One can justify much more effort on the inference engines. Indeed, that technology is well advanced.
182 | - The changeable parts of the application-peculiar materials are encoded in the rule base in a uniform fashion, and tools are provided for developing, changing, testing, and documenting the rule base. This regularizes much of the complexity of the application itself.
183 |
184 | Edward Feigenbaum says that the power of such systems does not come from ever-fancier inference mechanisms, but rather from ever-richer knowledge bases that reflect the real world more accurately. I believe the most important advance offered by the technology is the separation of the application complexity from the program itself.
185 |
186 | How can this be applied to the software task? In many ways: suggesting interface rules, advising on testing strategies, remembering but-type frequencies, offering optimization hints, etc.
187 |
188 | Consider an imaginary testing advisor, for example. In its most rudimentary form, the diagnostic expert system is very like a pilot’s checklist, fundamentally offering suggestions as to possible causes of difficulty. As the rule base is developed, the suggestions become more specific, taking more sophisticated account of the trouble symptoms reported. One can visualize a debugging assistant that offers very generalized suggestions at first, but as more and more system structure is embodied in the rule base, comes more and more particular in the hypotheses is generates and the tests it recommends. Such an expert system may depart most radically from the conventional ones in that its rule base should probably be hierarchically modularized in the same way the corresponding software product is, so that as the product is modularly modified, the diagnostic rule base can be modularly modified as well.
189 |
190 | The work required to generate the diagnostic rules is work that will have to be done anyway in generating the set of test cases for the modules and for the system. If it is done in a suitably general manner, with a uniform structure for rules and a good inference engine available, it may actually reduce the total labor of generating bring-up test cases, as well as helping in lifelong maintenance and modification testing. In the same way, we can postulate other advisors probably many of them and probably simple ones for the other parts of the software construction task.
191 |
192 | Many difficulties stand in the way of early realization of useful expert advisors to the program developer. A crucial part of our imaginary scenario is the development of easy ways to get from program structure specification to the automatic or semi-automatic generation of diagnostic rules. Even more difficult and important is the twofold task of knowledge acquisition: finding articulate, self-analytical experts who know why they do things; and developing efficient techniques for extracting what they know and distilling it into rule bases. The essential prerequisite for building an expert system is to have an expert.
193 |
194 | The most powerful contribution of expert systems will surely be to put at the service of the inexperienced programmer the experience and accumulated wisdom of the best programmers. This is no small contribution. The gap between the best software engineering practice and the average practice is very wide−perhaps wider than in any other engineering discipline. A tool that disseminates good practice would be important.
195 |
196 | **"Automatic" programming.** For almost 40 years, people have been anticipating and writing about “automatic programming”, the generation of a program for solving a problem from a statement of the problem specifications. Some people today write as if they expected this technology to provide the next breakthrough.7
197 |
198 | >Parnas implies that the term is used for glamour and not semantic content, asserting,
199 | *In short, automatic programming always has been a euphemism for programming with a higher-level language than was presently available to the programmer.8*
200 |
201 | He argues, in essence, that in most cases it is the solution method, not the problem, whose specification has to be given.
202 |
203 | Exceptions can be found. The technique of building generators is very powerful, and it is routinely used to good advantage in programs for sorting. Some systems for integrating differential equations have also permitted direct specification of the problem. The system assessed the parameters, chose from a library of methods of solution, and generated the programs.
204 |
205 | - These applications have very favorable properties. :
206 | - The problems are readily characterized by relatively few parameters.
207 | - There are many known methods of solution to provide a library of alternatives.
208 | - Extensive analysis has led to explicit rules for selecting solution techniques, given problem parameters.
209 |
210 | It is hard to see how such techniques generalize to the wider world of the ordinary software system, where cases with such neat properties are the exception. It is hard even to imagine how this breakthrough in generalization could conceivably occur.
211 |
212 | **Graphical programming.** A favorite subject for PH.D. dissertations in software engineering is graphical, or visual, programming, the application of computer graphics to software design.9 Sometimes the promise of such an approach is postulated from the analogy with VLSI chip design, where computer graphics plays so fruitful a role. Sometimes the approach is justified by considering flowcharts as the ideal program design medium, and providing powerful facilities for constructing them.
213 |
214 | Nothing even convincing, much less exciting, has yet emerged from such efforts. I am persuaded that nothing will.
215 |
216 | In the first place, as I have argued elsewhere, the flow chart is a very poor abstraction of software structure.10 Indeed, it is best viewed as Burks, von Neumann, and Goldstine’s attempt to provide a desperately needed high-level control language for their proposed computer. In the pitiful, multipage, connection-boxed form to which the flow chart has today been elaborated, it has proved to be essentially useless as a design-tool programmers draw flow charts after, not before, writing the programs they describe.
217 |
218 | Second, the screens of today are too small, in pixels, to show both the scope and the resolution of any serious detailed software diagram. The so-called “desktop metaphor” of today’s workstation is instead an “airplane-seat” metaphor. Anyone who has shuffled a lapful of papers while seated in a coach between two portly passengers will recognize the difference−one can see only a very few things at once. The true desktop provides overview of and random access to a score of pages. Moreover, when fits of creativity run strong, more than one programmer or writer has been known to abandon the desktop for the more spacious floor. The hardware technology will have to advance quite substantially before the scope of our scopes is sufficient to the software design task.
219 |
220 | More fundamentally, as I have argued above, software is very difficult to visualize. Whether we diagram control flow, variable scope nesting, variable cross-references, data blow, hierarchical data structures, or whatever, we feel only one dimension of the intricately interlocked software elephant. If we superimpose all the diagrams generated by the many relevant views, it is difficult to extract any global overview. The VLSI analogy is fundamentally misleading−a chip design is a layered two-dimensional object whose geometry reflects its essence. A software system is not.
221 |
222 | **Program verification.** Much of the effort in modern programming goes into the testing and repair of bugs. Is there perhaps a silver bullet to be found by eliminating the errors at the source, in the system design phase? Can both productivity and product reliability be radically enhance by following the profoundly different strategy of proving designs correct before the immense effort is poured into implementing and testing them?
223 |
224 | I do not believe we will find the magic here. Program verification is a very powerful concept, and it will be very important for such things as secure operating system kernels. The technology does not promise, however, to save labor. Verifications are so much work that only a few substantial programs have ever been verified.
225 |
226 | Program verification does not mean error-proof programs. There is no magic here, either. Mathematical proofs also can be faulty. So whereas verification might reduce the program-testing load, it cannot eliminate it.
227 |
228 | More seriously, even perfect program verification can only establish that a program meets its specification. The hardest part of the software task is arriving at a complete and consistent specification, and much of the essence of building a program is in fact the debugging of the specification.
229 |
230 |
231 | **Environments and tools.** How much more gain can be expected from the exploding researches into better programming environments? One’s instinctive reaction is that the big-payoff problems were the first attacked, and have been solved: hierarchical file systems, uniform file formats so as to have uniform program interfaces, and generalized tools. Language-specific smart editors are developments not yet widely used in practice, but the most they promise is freedom from syntactic errors and simple semantic errors.
232 |
233 | Perhaps the biggest gain yet to be realized in the programming environment is the use of integrated database systems to keep track of the myriads of details that must be recalled accurately by the individual programmer and kept current in a group of collaborators on a single system.
234 |
235 | Surely this work is worthwhile, and surely it will bear some fruit in both productivity and reliability. But by its very nature, the return from now on must be marginal.
236 |
237 |
238 | **Workstations.** What gains are to be expected for the software art from the certain and rapid increase in the power and memory capacity of the individual workstation? Well, how many MIPS can one use fruitfully? The composition and editing of programs and documents is fully supported by today’s speeds. Compiling could stand a boost, but a factor of 10 in machine speed would surely leave think-time the dominant activity in the programmer’s day. Indeed, it appears to be so now.
239 |
240 | More powerful workstations we surely welcome. Magical enhancements from them we cannot expect.
241 |
242 |
243 |
244 | ## Promising Attacks on the Conceptual Essence
245 | Even though no technological breakthrough promises to give the soft of magical results with which we are so familiar in the hardware area, there is both an abundance of good working going on now, and the promise of steady, if unspectacular progress.
246 |
247 | All of the technological attacks on the accidents of the software process are fundamentally limited by the productivity equation:
248 |
249 | Time of task = Σ (Frequency) i x (Time) i
250 |
251 | If, as I believe, the conceptual components of the task are now taking most of the time, then no amount of activity on the task components that are merely the expression of the concepts can give large productivity gains.
252 |
253 | Hence we must consider those attacks that address the essence of the software problem, the formulation of these complex conceptual structures. Fortunately, some of these are very promising.
254 |
255 | **Buy versus build.** The most radical possible solution for constructing software is not to construct it at all.
256 |
257 | Every day this becomes easier, as more and more vendors offer more and better software products for a dizzying variety of applications. While we software engineers have labored on production methodology, the personal computer revolution has created not one, but m any, mass markets for software. Every newsstand carried monthly magazines which, sorted by machine type, advertise and review dozens of products at prices from a few dollars to a few hundred dollars. More specialized sources offer very powerful products for the workstation and other Unix markets. Even software tolls and environments can be bought off-the-shelf. I have elsewhere proposed a market place for individual modules.
258 |
259 | Any such product is cheaper to buy than to build afresh. Even at a cost of $100,000, a purchased piece of software is costing only about as much as one programmer-year. And delivery is immediate! Immediate at least for products that really exist, products whose developer can refer the prospect to a happy user. Moreover, such products tend to be much better documented and somewhat better maintained than homegrown software.
260 |
261 | The development of the mass market is, I believe, the most profound long-run trend in software engineering. The cost of software has always been development cost, not replication cost. Sharing that cost among even a few users radically cuts the per-user cost. Another way of looking at it is that the use of n copies of a software system effectively multiplies the productivity of its developers by n. That is an enhancement of the productivity of the discipline and of the nation.
262 |
263 | The key issue, of course, is applicability. Can I use an available off-the-shelf package to do my task? A surprising thing has happened here. During the 1950s and 1960s, study after study showed that users would not use off-the-shelf packages for payroll, inventory control, accounts receivable, etc. The requirements were too specialized, the case-to-case variation too high. During the 1980s, we find such packages in high demand and widespread use. What has changed?
264 |
265 | Not really the packages. They may be somewhat more generalized and somewhat more customizable than formerly, but not much. Not really the applications, either. If anything, the business and scientific needs of today are more diverse, more complicated than those of 20 years ago.
266 |
267 | The big change has been in the hardware/software cost ratio. The buyer of a $2-million machine in 1960 felt that he could afford $250,000 more for a customized payroll program, one that slipped easily and nondisruptively into the computer-hostile social environment. Buyers of $50,000 office machines today cannot conceivably afford customized payroll programs; so they adapt their payroll procedures to the packages available. Computers are now so commonplace, if not yet so beloved, that the adaptations are accepted as a matter of course.
268 |
269 | There are dramatic exceptions to my argument that the generalization of the software packages has changed little over the years: electronic spreadsheets and simple database systems. These powerful tools, so obvious in retrospect and yet so late appearing, lend themselves to myriad uses, some quite unorthodox. Articles and even books now abound on how to tackle unexpected tasks with the spreadsheet. Large numbers of applications that would formerly have been written as custom programs in Cobol or Report Program Generator are now routinely done with these tools.
270 |
271 | Many users now operate their own computers day in and day out on varied applications without ever writing a program. Indeed, many of these users cannot write new programs for their machines, but they are nevertheless adept at solving new problems with them.
272 |
273 | I believe the single most powerful software productivity strategy for man organizations to day is to equip the computer-naïve intellectual workers on the firing line with personal computers and good generalized writing, drawing, file and spreadsheet programs, and turn them loose. The same strategy, with simple programming capabilities, will also work for hundreds of laboratory scientists.
274 |
275 |
276 |
277 | **Requirements refinement and rapid prototyping.** The hardest single part of building a software system is deciding precisely what to build. No other part of the conceptual work is to difficult as establishing the detailed technical requirements, including all the interfaces to people, to machines, and to other software systems. No other part of the work so cripples the resulting system if done wrong. No other part is more difficult go rectify later.
278 |
279 | Therefore the most important function that software builders do for their clients is the iterative extraction and refinement of the product requirements. For the truth is, the clients do not know what they want. They usually do not know what questions must be answered, and they almost never have thought of the problem in the detail that must be specified. Even the simple answer−”Make the new software system work like our old manual information-processing system” −is in fact too simple. Clients never want exactly that. Complex software systems are, moreover, things that act, that move, that work. The dynamics of that action are hard to imagine. So in planning any software activity, it is necessary to allow for an extensive iteration between the client and the designer as part of the system definition.
280 |
281 | I would go a step further and assert that it is really impossible for clients, even those working with software engineers, to specify completely, precisely, and correctly the exact requirements of a modern software product before having built and tried some versions of the product they are specifying.
282 |
283 | Therefore one of the most promising of the current technological efforts, and one which attacks the essence, not the accidents, of the software problem, is the development of approaches and tools for rapid prototyping of systems as part of the iterative specification of requirements.
284 |
285 | A prototype software system is one that simulates the important interfaces and performs the main functions of the intended system, while not being necessarily bound by the same hardware speed, size, or cost constraints. Prototypes typically perform the mainline tasks of the application, but make no attempt to handle the exceptions, respond correctly to invalid inputs, abort cleanly, etc. The purpose of the prototype is to make real the conceptual structure specified, so that the client can test it for consistency and usability
286 |
287 | Much of present-day software acquisition procedures rests upon the assumption that one can specify a satisfactory system in advance, get bids for its construction, have it built, and install it. I think this assumption is fundamentally wrong, and that many software acquisition problems spring from that fallacy. Hence they cannot be fixed without fundamental revision, one that provides for iterative development and specification of prototypes and products.
288 |
289 |
290 |
291 | **Incremental development−grow, not build, software.** I still remember the jolt I felt in 1958 when I first heard a friend talk about building a program, as opposed to writing one. In a flash be broadened my whole view of the software process. The metaphor shift was powerful, and accurate. Today we understand how like other building processes the construction of software is, and we freely use other elements of the metaphor, such as *specifications, assembly of components,* and *scaffolding.*
292 |
293 | The building metaphor has outlived its usefulness. It is time to change again. If, as I believe, the conceptual structures we construct today are too complicated to be accurately specified in advance, and too complex to be built faultlessly, then we must take a radically different approach.
294 |
295 | Let us turn to nature and study complexity in living things, instead of just the dead works of man. Here we find constructs whose complexities thrill us with awe. The brain alone is intricate beyond mapping, powerful beyond imitation, rich in diversity, self-protecting, and self-renewing. The secret is that it is grown, not built.
296 |
297 | So it must be with our software systems. Some years ago Harlan Mills proposed that any software system should be grown by incremental development.11 That is, the system should first be made to run, even though it does nothing useful except call the proper set of dummy subprograms. Then, bit-by-bit it is fleshed out, with the subprograms in turn being developed into actions or calls to empty stubs in the level below.
298 |
299 | I have seen the most dramatic results since I began urging this technique on the project builders in my software engineering laboratory class. Nothing in the past decade has so radically changed my own practice, or its effectiveness. The approach necessitates top-down design, for it is a top-down growing of the software. It allows easy backtracking. It lends itself to early prototypes. Each added function and new provision for more complex data or circumstances grown organically out of what is already there.
300 |
301 | The morale effects are startling. Enthusiasm jumps when there is a running system, even a simple one. Efforts redouble when the first picture from a new graphics software system appears on the screen, even if it is only a rectangle. One always has, at every stage in the process, a working system. I find that teams can grow much more complex entities in four months than they can *build*.
302 |
303 | The same benefits can be realized on large projects as on my small ones.12
304 |
305 |
306 | **Great designers.** The central question of how to improve the software art centers, as it always, on people.
307 |
308 | We can get good designs by following good practices instead of poor ones. Good design practices can be taught. Programmers are among the most intelligent part of the population, so they can learn good practice. Thus a major thrust in the United States is to promulgate good modern practice. New curricula, new literature, new organizations such as the Software Engineering Institute, all have come into being in order to raise the level of our practice from poor to good. This is entirely proper.
309 |
310 | Nevertheless, I do not believe we can make the next step upward in the same way. Whereas the difference between poor conceptual designs and good ones may lie in the soundness of design method, the difference between good designs and great ones surely does not. Great designs come from great designers. Software construction is a creative process. Sound methodology can empower and liberate the creative mind; it cannot enflame or inspire the drudge.
311 |
312 | The differences are not minor−it is rather like Salieri and Mozart. Study after study shows that the very best designers produce structures that are faster, smaller, simpler, cleaner, and produced with less effort. The differences between the great and the average approach an order of magnitude.
313 |
314 | A little retrospection shows that although many fine, useful software systems have been designed by committees and built by multipart projects, those software systems that have excited passionate fans are those that are the products of one or a few designing minds, great designers. Consider Unix, APL, Pascal, Modula, the Smalltalk interface, even Fortran; and contrast with Cobol, PL/I, Algol, MVS/370, and MS-DOS (fig. 1)
315 |
316 |
317 | |Yes| No|
318 | |----|-----|
319 | |Unix|Cobol|
320 | |APL|PL/1|
321 | |Pascal|Algol|
322 | |Modula|MVS/370|
323 | |Smalltalk|MS-DOS|
324 | |Fortran|
325 |
326 | *Fig. 1 Exciting products*
327 |
328 | Hence, although I strongly support the technology transfer and curriculum development efforts now underway, I think the most important single effort we can mount is to develop ways to grow great designers.
329 |
330 | No software organization can ignore this challenge. Good managers, scarce though they be, are no scarcer than good designers. Great designers and great managers are both very rare. Most organizations spend considerable effort in finding and cultivating the management prospects; I know of none that spends equal effort in finding and developing the great designers upon whom the technical excellence of the products will ultimately depend.
331 |
332 | My first proposal is that each software organization must determine and proclaim that great designers are as important to its success as great managers are, and that they can be expected to be similarly nurtured and rewarded. Not only salary, but the perquisites of recognition−office size, furnishings, personal technical equipment, travel funds, staff support−must be fully equivalent.
333 |
334 | How to grow great designers? Space does not permit a lengthy discussion, but some steps are obvious:
335 | - Systematically identify top designers as early as possible. The best are often not the most experienced.
336 | - Assign a career mentor to be responsible for the development of the prospect, and keep a careful career file.
337 | - Devise and maintain a career development plan for each prospect, including carefully selected apprenticeships with top designers, episodes of advanced formal education, and short courses, all interspersed with solo design and technical leadership assignments.
338 | - Provide opportunities for growing designers to interact with and stimulate each other.
--------------------------------------------------------------------------------
/docs/No Silver Bullet - Fred Brooks in (1986)[KOR]/README.md:
--------------------------------------------------------------------------------
1 | # No Silver Bullet —Essence and Accident in Software Engineering
2 | # 은 탄환은 없다 —소프트웨어공학의 본질과 위험성
3 |
4 | Frederick P. Brooks, Jr.
5 | University of North Carolina at Chapel Hill
6 |
7 | > There is no single development, in either technology or management technique,
8 | which by itself promises even one order-of-magnitude improvement within a decade in productivity,
9 | in reliability, in simplicity.
10 |
11 |
12 | ## Abstract1
13 | All software construction involves essential tasks,
14 | the fashioning of the complex conceptual structures that composethe abstract software entity,
15 | and accidental tasks, the representation of these abstract entities in programming languages
16 | and the mapping of these onto machine languages within space and speed constraints.
17 | Most of the big past gains in software productivity have come from removing artificial
18 | barriers that have made the accidental tasks inordinately hard,
19 | such as severe hardware constraints, awkward programming languages,
20 | lack of machine time. How much of what software engineers now do is
21 | still devoted to the accidental, as opposed to the essential?
22 | Unless it is more than 9/10 of all effort, shrinking all the accidental activities
23 | to zero time will not give an order of magnitude improvement.
24 |
25 | Therefore it appears that the time has come to address
26 | the essential parts of the software task,
27 | those concerned with fashioning abstract conceptual structures of great complexity.
28 | I suggest:
29 | - Exploiting the mass market to avoid constructing what can be bought.
30 | - Using rapid prototyping as part of a planned iteration in establishing software requirements.
31 | - Growing software organically, adding more and more function to systems as they are run, used, and tested.
32 | - Identifying and developing the great conceptual designers of the rising generation.
33 |
34 |
35 | ## Introduction
36 | Of all the monsters who fill the nightmares of our folklore,
37 | none terrify more than werewolves, because they transform unexpectedly
38 | from the familiar into horrors. For these, we seek bullets of silver
39 | than can magically lay them to rest.
40 |
41 | The familiar software project has something of this character
42 | (at least as seen by the non-technical manager),
43 | usually innocent and straightforward,
44 | but capable of becoming a monster of missed schedules, blown budgets,
45 | and flawed products. So we hear desperate cries for a silver bullet,
46 | something to make software costs drop as rapidly as computer hardware costs do.
47 |
48 | But, as we look to the horizon of a decade hence,
49 | we see no silver bullet. There is no single development,
50 | in either technology or management technique,
51 | which by itself promises even one order of magnitude improvement in productivity,
52 | in reliability, in simplicity. In this chapter we shall try to see why,
53 | but examining both the nature of the software problem and the properties of
54 | the bullets proposed.
55 |
56 | Skepticism is not pessimism, however.
57 | Although we see no startling breakthroughs,
58 | and indeed, believe such to be inconsistent with the nature of software,
59 | many encouraging innovations are under way.
60 | A disciplined, consistent effort to develop, propagate,
61 | and exploit them should indeed yield an order-of-magnitude improvement.
62 | There is no royal road, but there is a road.
63 |
64 | The first step toward the management of disease was replacement of
65 | demon theories and humours theories by the germ theory.
66 | That very step, the beginning of hope, in itself dashed all hopes of magical solutions.
67 | It told workers the progress would be made stepwise, at great effort,
68 | and that a persistent, unremitting care would have to be paid to a discipline of
69 | cleanliness. So it is with software engineering today.
70 |
71 |
72 |
73 | ## Does It Have To Be Hard? – Essential Difficulties
74 | Not only are there no silver bullets now in view, the very nature of software makes it unlikely that there will be any−no inventions that will do for software productivity, reliability, and simplicity what electronics, transistors, and large-scale integration did for computer hardware. We cannot expect ever to see twofold gains every two years.
75 |
76 | First, we must observe that the anomaly is not that software progress is so slow but that computer hardware progress is so fast. No other technology since civilization began has seen six orders of magnitude price-performance gain in 30 years. In no other technology can one choose to take the gain in either improved performance or in reduced costs. These gains flow from the transformation of computer manufacture from an assembly industry into a process industry.
77 |
78 | Second, to see what rate of progress we can expect in software technology, let us examine its difficulties. Following Aristotle, I divide them into essence−the difficulties inherent in the nature of the software−and accidents−those difficulties that today attend its production but that are not inherent.
79 |
80 | The accidents I discuss in the next section. First let us consider the essence.
81 |
82 | The essence of a software entity is a construct of interlocking concepts: data sets, relationships among data items, algorithms, and invocations of functions. This essence is abstract, in that the conceptual construct is the same under many different representations. It is nonetheless highly precise and richly detailed.
83 |
84 | I believe the hard part of building software to be the specification, design, and testing of this conceptual construct, not the labor of representing it and testing the fidelity of the representation. We still make syntax errors, to be sure; but they are fuzz compared to the conceptual errors in most systems.
85 |
86 | If this is true, building software will always be hard. There is inherently no silver bullet.
87 |
88 | Let us consider the inherent properties of this irreducible essence of modern software systems: complexity, conformity, changeability, and invisibility.
89 |
90 | **Complexity.** Software entities are more complex for their size than perhaps any other human construct, because no two parts are alike (at least above the statement level). If they are, we make the two similar parts into one, a subroutine, open or closed. In this respect software systems differ profoundly from computers, buildings, or automobiles, where repeated elements abound.
91 |
92 | Digital computers are themselves more complex than most things people build; they have very large numbers of states. This makes conceiving, describing, and testing them hard. Software systems have orders of magnitude more states than computers do.
93 |
94 | Likewise, a scaling-up of a software entity is not merely a repetition of the same elements in larger size; it is necessarily an increase in the number of different elements. In most cases, the elements interact with each other in some nonlinear fashion, and the complexity of the whole increases much more than linearly.
95 |
96 | The complexity of software is in essential property, not an accidental one. Hence descriptions of a software entity that abstract away its complexity often abstract away its essence. Mathematics and the physical sciences made great strides for three centuries by constructing simplified models of complex phenomena, deriving properties from the models, and verifying those properties experimentally. This worked because the complexities ignored in the models were not the essential properties of the phenomena. It does not work when the complexities are the essence.
97 |
98 | Many of the classical problems of developing software products derived from this essential complexity and its nonlinear increased with size. From the complexity comes the difficulty of communication among team members, which leads to product flaws, cost overruns, schedule delays. From the complexity comes the difficulty of enumerating, much less understanding, all the possible states of the program, and from that comes the unreliability. From the complexity of the functions comes the difficulty of invoking those functions, which makes programs hard to use. From complexity of structure comes the difficulty of extending programs to new functions without creating side effects. From the complexity of structure comes the unvisualized state that that constitute security trapdoors.
99 |
100 | Not only technical problems but management problems as well come from the complexity. This complexity makes overview hard, thus impeding conceptual integrity. It makes it hard to find and control all the loose ends. It creates the tremendous learning and understanding burden that makes personnel turnover a disaster.
101 |
102 | **Conformity.** Software people are not alone in facing complexity. Physics deals with terribly complex objects even at the “fundamental” particle level. The physicist labors on, however, in a firm faith that there are unifying principles to be found, whether in quarks or in unified field theories. Einstein repeatedly argued that there must be simplified explanations of nature, because God is not capricious or arbitrary.
103 |
104 | No such faith comforts the software engineer. Much of the complexity he must master is arbitrary complexity, forced without rhyme or reason by the many human institutions and systems to which his interfaces must confirm. These differ from interface to interface, and from time to time, not because of necessity but only because they were designed by different people, rather than by God.
105 |
106 | In many cases the software must confirm because it has most recently come to the scene. In others it must conform because it is perceived as the most conformable. But in all cases, much complexity comes from conformation to other interfaces; this cannot be simplified out by any redesign of the software alone.
107 |
108 | **Changeability.** The software entity is constantly subject to pressures for change. Of course, so are buildings, cars, and computers. But manufactured things are infrequently changed after manufacture; they are superseded by later models, or essential changes are incorporated in later serial-number copies of the same basic design. Callbacks of automobiles are really quite infrequent; field changes of computers somewhat less so. Both are much less frequent than modifications to fielded software.
109 |
110 | Partly this is because the software in a system embodies its function, and the function is the part that most feels the pressures of change. Partly it is because software can be changed more easily−it is pure thought-stuff, infinitely malleable. Buildings do in fact get changed, but the high costs of change, understood by all, serve to dampen the whim of the changers.
111 |
112 | All successful software gets changed. Two processes are at work. As a software product is found to be useful, people try it in new cases at the edge of, or beyond, the original domain. The pressures for extended function come chiefly from users who like the basic function and invent new uses for it.
113 |
114 | Second, successful software also survives beyond the normal life of the machine vehicle for which it is first written. If not new computers, then at least new disks, new displays, new printers come along; and the software must be conformed to its new vehicles of opportunity.
115 |
116 | In short, the software product is embedded in a cultural matrix of applications, users, laws, and machine vehicles. These all change continually, and their changes inexorably force change upon the software product.
117 |
118 | **Invisibility.** Software is invisible and unvisualizable. Geometric abstractions are powerful tools. The floor plan of a building helps both architect and client evaluate spaces, traffic flows, and views. Contradictions become obvious, omissions can be caught. Scale drawings of mechanical parts and stick-figure models of molecules, although abstractions, serve the same purpose. A geometric reality is captured in a geometric abstraction.
119 |
120 | The reality of software is not inherently embedded in space. Hence it has no ready geometric representation in the way that land has maps, silicon chips have diagrams, computers have connectivity schematics. As soon as we attempt to diagram software structure, we find it to constitute not one, but several, general directed graphs, superimposed one upon another. The several graphs may represent the flow of control, the flow of data, patterns of dependency, time sequence, name-space relationships. These are usually not even planar, much less hierarchical. Indeed, one of the ways of establishing conceptual control over such structure is to enforce link cutting until one or more of the graphs becomes hierarchical.2
121 |
122 | In spite of progress in restricting and simplifying the structures of software, they remain inherently unvisualizable, thus depriving the mind of some of its most powerful conceptual tools. This lack not only impedes the process of design within one mind, it severely hinders communication among minds.
123 |
124 |
125 | ## Past Breakthroughs Solved Accidental Difficulties
126 | If we examine the three steps in software technology that have been most fruitful in the past, we discover that each attacked a different major difficulty in building software, but they have been the accidental, not the essential, difficulties. We can also see the natural limits to the extrapolation of each such attack.
127 |
128 | **High-level languages.** Surely the most powerful stroke for software productivity, reliability, and simplicity has been the progressive use of high-level languages for programming. Most observers credit that development with at least a factor of five in productivity, and with concomitant gains in reliability, simplicity, and comprehensibility
129 |
130 | What does a high-level language accomplish? It frees a program from much of its accidental complexity. An abstract program consists of conceptual constructs: operations, data types, sequences, and communication. The concrete machine program is concerned with bits, registers, conditions, branches, channels, disks, and such. To the extent that the high-level language embodies the constructs wanted in the abstract program and avoids all lower ones, it eliminates a whole level of complexity that was never inherent in the program at all.
131 |
132 | The most a high-level language can do is to furnish all the constructs the programmer imagines in the abstract program. To be sure, the level of our sophistication in thinking about data structures, data types, and operations is steadily rising, but at an ever-decreasing rate. And language development approaches closer and closer to the sophistication of users.
133 |
134 | Moreover, at some point the elaboration of a high-level language becomes a burden that increases, not reduces, the intellectual task of the user who rarely uses the esoteric constructs.
135 |
136 | **Time-sharing.** Most observers credit time-sharing with a major improvement in the productivity of programmers and in the quality of their product, although not so large as that brought by high-level languages.
137 |
138 | Time-sharing attacks a distinctly different difficulty. Time-sharing preserves immediacy, and hence enables us to maintain an overview of complexity. The slow turnaround of batch programming means that we inevitably forget the minutiae, if not the very thrust, of what we were thinking when we stopped programming and called for compilation and execution. This interruption of consciousness is costly in time, for we must refresh. The most serious effect may well be the decay of grasp of all that is going on in a complex system.
139 |
140 | Slow turn-around, like machine-language complexities, is an accidental rather than an essential difficulty of the software process. The limits of the contribution of time-sharing derive directly. The principle effect is to shorten system response time. As it goes to zero, at some point it passes the human threshold of noticeability, about 100 milliseconds. Beyond that no benefits are to be expected.
141 |
142 | **Unified programming environments.** Unix and Interlisp, the first integrated programming environments to come into widespread use, are perceived to have improved productivity by integral factors. Why?
143 |
144 | They attack the accidental difficulties of using programs together, by providing integrated libraries, unified file formats, and piles and filters. As a result, conceptual structures that in principle could always call, feed, and use one another can indeed easily do so in practice.
145 |
146 | This breakthrough in turn stimulated the development of whole toolbenches, since each new tool could be applied to any programs by using the standard formats.
147 |
148 | Because of these successes, environments are the subject of much of today’s software engineering research. We will look at their promise and limitations in the next section.
149 |
150 |
151 | ## Hopes for the Silver
152 | Now lets us consider the technical developments that are most often advanced as potential silver bullets. What problems do they address? Are they the problems of essence, or are they remainders of our accidental difficulties? Do they offer revolutionary advances, or incremental ones?
153 |
154 | **Ada and other high-level language advances.** One of the most touted recent developments is the programming language Ada, a general-purpose, high-level language of the 1980s. Ada indeed not only reflects evolutionary improvements in language concepts but embodies features to encourage modern design and modularization concepts. Perhaps the Ada philosophy is more of an advance than the Ada language, for it is the philosophy of modularization, of abstract data types, of hierarchical structuring. Ada is perhaps over-rich, the natural product of the process by which requirements were laid on its design. That is not fatal, for subset working vocabularies can solve the learning problem, and hardware advances will give us the cheap MIPS to pay for the compiling costs. Advancing the structuring of software systems is indeed a very good use for the increased MIPS our dollars will buy. Operating systems, loudly decried in the 1960s for their memory and cycle costs, have proved to be an excellent form in which to use some of the MIPS and cheap memory bytes of the past hardware surge.
155 |
156 | Nevertheless, Ada will not prove to be the silver bullet that slays the software productivity monster. It is, after all, just another high-level language, and the biggest payoff from such languages came from the first transition, up from the accidental complexities of the machine into the more abstract statement of step-by-step solutions. Once those accidents have been removed, the remaining ones are smaller, and the payoff from their removal will surely be less.
157 |
158 | I predict that a decade from now, when the effectiveness of Ada is assessed, it will be seen to have made a substantial difference, but not because of any particular language feature, nor indeed because of all of them combined. Neither will the new Ada environment prove to be the cause of the improvements. Ada’s greatest contribution will be that switching to it occasioned training programmers in modern software design techniques.
159 |
160 | **Object-oriented programming.** Many students of the art hold out more hope for object-oriented programming than for any of the other technical fads of the day.3 I am among them. Mark Sherman of Dartmouth notes that we must be careful to distinguish two separate ideas that go under that name: abstract data types and hierarchical types, also called classes. The concept of the abstract data type is that an object’s type should be defined by a name, a set of proper values, and a set of proper operations, rather than its storage structure, which should be hidden. Examples are Ada packages (with private types) or Modula’s modules.
161 |
162 | Hierarchical types, such as Simula-67’s classes, allow the definition of general interfaces that can be further refined by providing subordinate types. The two concepts are orthogonal−there may be hierarchies without hiding and hiding without hierarchies. Both concepts represent real advances in the art of building software.
163 |
164 | Each removes one more accidental difficulty from the process, allowing the designer to express the essence of his design without having to express large amounts of syntactic material that add no new information content. For both abstract types and hierarchical types, the result is to remove a higher-order sort of accidental difficulty and allow a higher-order expression of design.
165 |
166 | Nevertheless, such advances can do no more than to remove all the accidental difficulties from the expression of the design. The complexity of the design itself is essential; and such attacks make no change whatever in that. An order-of-magnitude gain can be made by object-oriented programming only if the unnecessary underbrush of type specification remaining today in our programming language is itself responsible for nine-tenths of the work involved in designing a program product. I doubt it.
167 |
168 | **Artificial intelligence.** Many people expect advances in artificial intelligence to provide the revolutionary breakthrough that will give order-of-magnitude gains in software productivity and quality.4 I do not. To see why, we must dissect what is meant by “artificial intelligence” and then see how it applies.
169 | >**Parnas has clarified the terminological chaos:**
170 | *Two quite different definitions of AI are in common use today. AI-1: The use of computers to solve problems that previously could only be solved by applying human intelligence. AI-2: The use of a specific set of programming techniques knows as heuristic or rule-based programming. In this approach human experts are studies to determine what heuristics or rules of thumb they use in solving problems... The program is designed to solve a problem the way that humans seem to solve it.
171 | The first definition has a sliding meaning... Something can fit the definition of AI-1 today but, once we see how the program works and understand the problem, we will not think of it as AI anymore... Unfortunately I cannot identify a body of technology that is unique to this field... Most of the work is problem-specific, and some abstraction or creativity is require to see how to transfer it.5*
172 |
173 | I agree completely with this critique. The techniques used for speech recognition seem to have little in common with those used for image recognition, and both are different from those used in expert systems. I have a hard time seeing how image recognition, for example, will make any appreciable difference in programming practice. The same is try of speech recognition. The hard thing about building software is deciding what to say, not saying it. No facilitation of expression can give more than marginal gains.
174 |
175 | Expert systems technology, AI-2, deserves a section of its own.
176 |
177 | **Expert systems.** The most advanced part of the artificial intelligence art, and the most widely applies, is the technology for building expert systems. Many software scientists are hard at work applying this technology to the software-building environment.6 What is the concept, and what are the prospects?
178 |
179 | An expert system is a program containing a generalized inference engine and a rule base, designed to take input data and assumptions and explore the logical consequences through the inferences derivable from the rule base, yielding conclusions and advice, and offering to explain its results by retracing its reasoning for the user. The inference engines typically can deal with fuzzy or probabilistic data and rules in addition to purely deterministic logic.
180 |
181 | Such systems offer some clear advantages over programmed algorithms for arriving at the same solutions to the same problems:
182 | - Inference engine technology is developed in an application-independent way, and then applied to many uses. One can justify much more effort on the inference engines. Indeed, that technology is well advanced.
183 | - The changeable parts of the application-peculiar materials are encoded in the rule base in a uniform fashion, and tools are provided for developing, changing, testing, and documenting the rule base. This regularizes much of the complexity of the application itself.
184 |
185 | Edward Feigenbaum says that the power of such systems does not come from ever-fancier inference mechanisms, but rather from ever-richer knowledge bases that reflect the real world more accurately. I believe the most important advance offered by the technology is the separation of the application complexity from the program itself.
186 |
187 | How can this be applied to the software task? In many ways: suggesting interface rules, advising on testing strategies, remembering but-type frequencies, offering optimization hints, etc.
188 |
189 | Consider an imaginary testing advisor, for example. In its most rudimentary form, the diagnostic expert system is very like a pilot’s checklist, fundamentally offering suggestions as to possible causes of difficulty. As the rule base is developed, the suggestions become more specific, taking more sophisticated account of the trouble symptoms reported. One can visualize a debugging assistant that offers very generalized suggestions at first, but as more and more system structure is embodied in the rule base, comes more and more particular in the hypotheses is generates and the tests it recommends. Such an expert system may depart most radically from the conventional ones in that its rule base should probably be hierarchically modularized in the same way the corresponding software product is, so that as the product is modularly modified, the diagnostic rule base can be modularly modified as well.
190 |
191 | The work required to generate the diagnostic rules is work that will have to be done anyway in generating the set of test cases for the modules and for the system. If it is done in a suitably general manner, with a uniform structure for rules and a good inference engine available, it may actually reduce the total labor of generating bring-up test cases, as well as helping in lifelong maintenance and modification testing. In the same way, we can postulate other advisors probably many of them and probably simple ones for the other parts of the software construction task.
192 |
193 | Many difficulties stand in the way of early realization of useful expert advisors to the program developer. A crucial part of our imaginary scenario is the development of easy ways to get from program structure specification to the automatic or semi-automatic generation of diagnostic rules. Even more difficult and important is the twofold task of knowledge acquisition: finding articulate, self-analytical experts who know why they do things; and developing efficient techniques for extracting what they know and distilling it into rule bases. The essential prerequisite for building an expert system is to have an expert.
194 |
195 | The most powerful contribution of expert systems will surely be to put at the service of the inexperienced programmer the experience and accumulated wisdom of the best programmers. This is no small contribution. The gap between the best software engineering practice and the average practice is very wide−perhaps wider than in any other engineering discipline. A tool that disseminates good practice would be important.
196 |
197 | **"Automatic" programming.** For almost 40 years, people have been anticipating and writing about “automatic programming”, the generation of a program for solving a problem from a statement of the problem specifications. Some people today write as if they expected this technology to provide the next breakthrough.7
198 |
199 | >Parnas implies that the term is used for glamour and not semantic content, asserting,
200 | *In short, automatic programming always has been a euphemism for programming with a higher-level language than was presently available to the programmer.8*
201 |
202 | He argues, in essence, that in most cases it is the solution method, not the problem, whose specification has to be given.
203 |
204 | Exceptions can be found. The technique of building generators is very powerful, and it is routinely used to good advantage in programs for sorting. Some systems for integrating differential equations have also permitted direct specification of the problem. The system assessed the parameters, chose from a library of methods of solution, and generated the programs.
205 |
206 | - These applications have very favorable properties. :
207 | - The problems are readily characterized by relatively few parameters.
208 | - There are many known methods of solution to provide a library of alternatives.
209 | - Extensive analysis has led to explicit rules for selecting solution techniques, given problem parameters.
210 |
211 | It is hard to see how such techniques generalize to the wider world of the ordinary software system, where cases with such neat properties are the exception. It is hard even to imagine how this breakthrough in generalization could conceivably occur.
212 |
213 | **Graphical programming.** A favorite subject for PH.D. dissertations in software engineering is graphical, or visual, programming, the application of computer graphics to software design.9 Sometimes the promise of such an approach is postulated from the analogy with VLSI chip design, where computer graphics plays so fruitful a role. Sometimes the approach is justified by considering flowcharts as the ideal program design medium, and providing powerful facilities for constructing them.
214 |
215 | Nothing even convincing, much less exciting, has yet emerged from such efforts. I am persuaded that nothing will.
216 |
217 | In the first place, as I have argued elsewhere, the flow chart is a very poor abstraction of software structure.10 Indeed, it is best viewed as Burks, von Neumann, and Goldstine’s attempt to provide a desperately needed high-level control language for their proposed computer. In the pitiful, multipage, connection-boxed form to which the flow chart has today been elaborated, it has proved to be essentially useless as a design-tool programmers draw flow charts after, not before, writing the programs they describe.
218 |
219 | Second, the screens of today are too small, in pixels, to show both the scope and the resolution of any serious detailed software diagram. The so-called “desktop metaphor” of today’s workstation is instead an “airplane-seat” metaphor. Anyone who has shuffled a lapful of papers while seated in a coach between two portly passengers will recognize the difference−one can see only a very few things at once. The true desktop provides overview of and random access to a score of pages. Moreover, when fits of creativity run strong, more than one programmer or writer has been known to abandon the desktop for the more spacious floor. The hardware technology will have to advance quite substantially before the scope of our scopes is sufficient to the software design task.
220 |
221 | More fundamentally, as I have argued above, software is very difficult to visualize. Whether we diagram control flow, variable scope nesting, variable cross-references, data blow, hierarchical data structures, or whatever, we feel only one dimension of the intricately interlocked software elephant. If we superimpose all the diagrams generated by the many relevant views, it is difficult to extract any global overview. The VLSI analogy is fundamentally misleading−a chip design is a layered two-dimensional object whose geometry reflects its essence. A software system is not.
222 |
223 | **Program verification.** Much of the effort in modern programming goes into the testing and repair of bugs. Is there perhaps a silver bullet to be found by eliminating the errors at the source, in the system design phase? Can both productivity and product reliability be radically enhance by following the profoundly different strategy of proving designs correct before the immense effort is poured into implementing and testing them?
224 |
225 | I do not believe we will find the magic here. Program verification is a very powerful concept, and it will be very important for such things as secure operating system kernels. The technology does not promise, however, to save labor. Verifications are so much work that only a few substantial programs have ever been verified.
226 |
227 | Program verification does not mean error-proof programs. There is no magic here, either. Mathematical proofs also can be faulty. So whereas verification might reduce the program-testing load, it cannot eliminate it.
228 |
229 | More seriously, even perfect program verification can only establish that a program meets its specification. The hardest part of the software task is arriving at a complete and consistent specification, and much of the essence of building a program is in fact the debugging of the specification.
230 |
231 |
232 | **Environments and tools.** How much more gain can be expected from the exploding researches into better programming environments? One’s instinctive reaction is that the big-payoff problems were the first attacked, and have been solved: hierarchical file systems, uniform file formats so as to have uniform program interfaces, and generalized tools. Language-specific smart editors are developments not yet widely used in practice, but the most they promise is freedom from syntactic errors and simple semantic errors.
233 |
234 | Perhaps the biggest gain yet to be realized in the programming environment is the use of integrated database systems to keep track of the myriads of details that must be recalled accurately by the individual programmer and kept current in a group of collaborators on a single system.
235 |
236 | Surely this work is worthwhile, and surely it will bear some fruit in both productivity and reliability. But by its very nature, the return from now on must be marginal.
237 |
238 |
239 | **Workstations.** What gains are to be expected for the software art from the certain and rapid increase in the power and memory capacity of the individual workstation? Well, how many MIPS can one use fruitfully? The composition and editing of programs and documents is fully supported by today’s speeds. Compiling could stand a boost, but a factor of 10 in machine speed would surely leave think-time the dominant activity in the programmer’s day. Indeed, it appears to be so now.
240 |
241 | More powerful workstations we surely welcome. Magical enhancements from them we cannot expect.
242 |
243 |
244 |
245 | ## Promising Attacks on the Conceptual Essence
246 | Even though no technological breakthrough promises to give the soft of magical results with which we are so familiar in the hardware area, there is both an abundance of good working going on now, and the promise of steady, if unspectacular progress.
247 |
248 | All of the technological attacks on the accidents of the software process are fundamentally limited by the productivity equation:
249 |
250 | Time of task = Σ (Frequency) i x (Time) i
251 |
252 | If, as I believe, the conceptual components of the task are now taking most of the time, then no amount of activity on the task components that are merely the expression of the concepts can give large productivity gains.
253 |
254 | Hence we must consider those attacks that address the essence of the software problem, the formulation of these complex conceptual structures. Fortunately, some of these are very promising.
255 |
256 | **Buy versus build.** The most radical possible solution for constructing software is not to construct it at all.
257 |
258 | Every day this becomes easier, as more and more vendors offer more and better software products for a dizzying variety of applications. While we software engineers have labored on production methodology, the personal computer revolution has created not one, but m any, mass markets for software. Every newsstand carried monthly magazines which, sorted by machine type, advertise and review dozens of products at prices from a few dollars to a few hundred dollars. More specialized sources offer very powerful products for the workstation and other Unix markets. Even software tolls and environments can be bought off-the-shelf. I have elsewhere proposed a market place for individual modules.
259 |
260 | Any such product is cheaper to buy than to build afresh. Even at a cost of $100,000, a purchased piece of software is costing only about as much as one programmer-year. And delivery is immediate! Immediate at least for products that really exist, products whose developer can refer the prospect to a happy user. Moreover, such products tend to be much better documented and somewhat better maintained than homegrown software.
261 |
262 | The development of the mass market is, I believe, the most profound long-run trend in software engineering. The cost of software has always been development cost, not replication cost. Sharing that cost among even a few users radically cuts the per-user cost. Another way of looking at it is that the use of n copies of a software system effectively multiplies the productivity of its developers by n. That is an enhancement of the productivity of the discipline and of the nation.
263 |
264 | The key issue, of course, is applicability. Can I use an available off-the-shelf package to do my task? A surprising thing has happened here. During the 1950s and 1960s, study after study showed that users would not use off-the-shelf packages for payroll, inventory control, accounts receivable, etc. The requirements were too specialized, the case-to-case variation too high. During the 1980s, we find such packages in high demand and widespread use. What has changed?
265 |
266 | Not really the packages. They may be somewhat more generalized and somewhat more customizable than formerly, but not much. Not really the applications, either. If anything, the business and scientific needs of today are more diverse, more complicated than those of 20 years ago.
267 |
268 | The big change has been in the hardware/software cost ratio. The buyer of a $2-million machine in 1960 felt that he could afford $250,000 more for a customized payroll program, one that slipped easily and nondisruptively into the computer-hostile social environment. Buyers of $50,000 office machines today cannot conceivably afford customized payroll programs; so they adapt their payroll procedures to the packages available. Computers are now so commonplace, if not yet so beloved, that the adaptations are accepted as a matter of course.
269 |
270 | There are dramatic exceptions to my argument that the generalization of the software packages has changed little over the years: electronic spreadsheets and simple database systems. These powerful tools, so obvious in retrospect and yet so late appearing, lend themselves to myriad uses, some quite unorthodox. Articles and even books now abound on how to tackle unexpected tasks with the spreadsheet. Large numbers of applications that would formerly have been written as custom programs in Cobol or Report Program Generator are now routinely done with these tools.
271 |
272 | Many users now operate their own computers day in and day out on varied applications without ever writing a program. Indeed, many of these users cannot write new programs for their machines, but they are nevertheless adept at solving new problems with them.
273 |
274 | I believe the single most powerful software productivity strategy for man organizations to day is to equip the computer-naïve intellectual workers on the firing line with personal computers and good generalized writing, drawing, file and spreadsheet programs, and turn them loose. The same strategy, with simple programming capabilities, will also work for hundreds of laboratory scientists.
275 |
276 |
277 |
278 | **Requirements refinement and rapid prototyping.** The hardest single part of building a software system is deciding precisely what to build. No other part of the conceptual work is to difficult as establishing the detailed technical requirements, including all the interfaces to people, to machines, and to other software systems. No other part of the work so cripples the resulting system if done wrong. No other part is more difficult go rectify later.
279 |
280 | Therefore the most important function that software builders do for their clients is the iterative extraction and refinement of the product requirements. For the truth is, the clients do not know what they want. They usually do not know what questions must be answered, and they almost never have thought of the problem in the detail that must be specified. Even the simple answer−”Make the new software system work like our old manual information-processing system” −is in fact too simple. Clients never want exactly that. Complex software systems are, moreover, things that act, that move, that work. The dynamics of that action are hard to imagine. So in planning any software activity, it is necessary to allow for an extensive iteration between the client and the designer as part of the system definition.
281 |
282 | I would go a step further and assert that it is really impossible for clients, even those working with software engineers, to specify completely, precisely, and correctly the exact requirements of a modern software product before having built and tried some versions of the product they are specifying.
283 |
284 | Therefore one of the most promising of the current technological efforts, and one which attacks the essence, not the accidents, of the software problem, is the development of approaches and tools for rapid prototyping of systems as part of the iterative specification of requirements.
285 |
286 | A prototype software system is one that simulates the important interfaces and performs the main functions of the intended system, while not being necessarily bound by the same hardware speed, size, or cost constraints. Prototypes typically perform the mainline tasks of the application, but make no attempt to handle the exceptions, respond correctly to invalid inputs, abort cleanly, etc. The purpose of the prototype is to make real the conceptual structure specified, so that the client can test it for consistency and usability
287 |
288 | Much of present-day software acquisition procedures rests upon the assumption that one can specify a satisfactory system in advance, get bids for its construction, have it built, and install it. I think this assumption is fundamentally wrong, and that many software acquisition problems spring from that fallacy. Hence they cannot be fixed without fundamental revision, one that provides for iterative development and specification of prototypes and products.
289 |
290 |
291 |
292 | **Incremental development−grow, not build, software.** I still remember the jolt I felt in 1958 when I first heard a friend talk about building a program, as opposed to writing one. In a flash be broadened my whole view of the software process. The metaphor shift was powerful, and accurate. Today we understand how like other building processes the construction of software is, and we freely use other elements of the metaphor, such as *specifications, assembly of components,* and *scaffolding.*
293 |
294 | The building metaphor has outlived its usefulness. It is time to change again. If, as I believe, the conceptual structures we construct today are too complicated to be accurately specified in advance, and too complex to be built faultlessly, then we must take a radically different approach.
295 |
296 | Let us turn to nature and study complexity in living things, instead of just the dead works of man. Here we find constructs whose complexities thrill us with awe. The brain alone is intricate beyond mapping, powerful beyond imitation, rich in diversity, self-protecting, and self-renewing. The secret is that it is grown, not built.
297 |
298 | So it must be with our software systems. Some years ago Harlan Mills proposed that any software system should be grown by incremental development.11 That is, the system should first be made to run, even though it does nothing useful except call the proper set of dummy subprograms. Then, bit-by-bit it is fleshed out, with the subprograms in turn being developed into actions or calls to empty stubs in the level below.
299 |
300 | I have seen the most dramatic results since I began urging this technique on the project builders in my software engineering laboratory class. Nothing in the past decade has so radically changed my own practice, or its effectiveness. The approach necessitates top-down design, for it is a top-down growing of the software. It allows easy backtracking. It lends itself to early prototypes. Each added function and new provision for more complex data or circumstances grown organically out of what is already there.
301 |
302 | The morale effects are startling. Enthusiasm jumps when there is a running system, even a simple one. Efforts redouble when the first picture from a new graphics software system appears on the screen, even if it is only a rectangle. One always has, at every stage in the process, a working system. I find that teams can grow much more complex entities in four months than they can *build*.
303 |
304 | The same benefits can be realized on large projects as on my small ones.12
305 |
306 |
307 | **Great designers.** The central question of how to improve the software art centers, as it always, on people.
308 |
309 | We can get good designs by following good practices instead of poor ones. Good design practices can be taught. Programmers are among the most intelligent part of the population, so they can learn good practice. Thus a major thrust in the United States is to promulgate good modern practice. New curricula, new literature, new organizations such as the Software Engineering Institute, all have come into being in order to raise the level of our practice from poor to good. This is entirely proper.
310 |
311 | Nevertheless, I do not believe we can make the next step upward in the same way. Whereas the difference between poor conceptual designs and good ones may lie in the soundness of design method, the difference between good designs and great ones surely does not. Great designs come from great designers. Software construction is a creative process. Sound methodology can empower and liberate the creative mind; it cannot enflame or inspire the drudge.
312 |
313 | The differences are not minor−it is rather like Salieri and Mozart. Study after study shows that the very best designers produce structures that are faster, smaller, simpler, cleaner, and produced with less effort. The differences between the great and the average approach an order of magnitude.
314 |
315 | A little retrospection shows that although many fine, useful software systems have been designed by committees and built by multipart projects, those software systems that have excited passionate fans are those that are the products of one or a few designing minds, great designers. Consider Unix, APL, Pascal, Modula, the Smalltalk interface, even Fortran; and contrast with Cobol, PL/I, Algol, MVS/370, and MS-DOS (fig. 1)
316 |
317 |
318 | |Yes| No|
319 | |----|-----|
320 | |Unix|Cobol|
321 | |APL|PL/1|
322 | |Pascal|Algol|
323 | |Modula|MVS/370|
324 | |Smalltalk|MS-DOS|
325 | |Fortran|
326 |
327 | *Fig. 1 Exciting products*
328 |
329 | Hence, although I strongly support the technology transfer and curriculum development efforts now underway, I think the most important single effort we can mount is to develop ways to grow great designers.
330 |
331 | No software organization can ignore this challenge. Good managers, scarce though they be, are no scarcer than good designers. Great designers and great managers are both very rare. Most organizations spend considerable effort in finding and cultivating the management prospects; I know of none that spends equal effort in finding and developing the great designers upon whom the technical excellence of the products will ultimately depend.
332 |
333 | My first proposal is that each software organization must determine and proclaim that great designers are as important to its success as great managers are, and that they can be expected to be similarly nurtured and rewarded. Not only salary, but the perquisites of recognition−office size, furnishings, personal technical equipment, travel funds, staff support−must be fully equivalent.
334 |
335 | How to grow great designers? Space does not permit a lengthy discussion, but some steps are obvious:
336 | - Systematically identify top designers as early as possible. The best are often not the most experienced.
337 | - Assign a career mentor to be responsible for the development of the prospect, and keep a careful career file.
338 | - Devise and maintain a career development plan for each prospect, including carefully selected apprenticeships with top designers, episodes of advanced formal education, and short courses, all interspersed with solo design and technical leadership assignments.
339 | - Provide opportunities for growing designers to interact with and stimulate each other.
340 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # To Become a Better Programmer
2 |
3 | ## 설명
4 |
5 | Description에도 써있다시피 jwasham의 Coding Interview University에서 영감을 받아 시작하게 되었다.
6 | 약간의 차이가 있다면 Interview University라는 이름과는 달리 코딩 면접을 위한 프로젝트는 아니라는 점이다.
7 | 그냥 스스로도 더 나은 프로그래머가 되고 싶어서, 또 한글로 된 양질의 자료도 많은데 파편화돼있는 게 아쉬워서 시작하게 됐다.
8 | 그래서 저장소의 이름 자체도 To Become a Better Programmer(더 나은 프로그래머 되기)로 정하였다.
9 |
10 | 되도록이면 한글로 된 자료 중에 쉽고 알아보기 쉬운 자료를 모을 것이지만 영어로 된 자료도 있을 것이다.
11 | 목차나 내용은 jwasham의 Coding Interview University을 참고할 것이나 완전히 같지는 않을 것이며, 정렬은 특수문자를 제외한 123->abc->가나다 순서이다.
12 | 그리고 [내 블로그](https://this-programmer.tistory.com/)에 있는 글들도 이용할 예정이다.
13 |
14 | ## 목차
15 |
16 | - [To Become a Better Programmer](#to-become-a-better-programmer)
17 | - [설명](#설명)
18 | - [목차](#목차)
19 | - [강의](#강의)
20 | - [검색](#검색)
21 | - [기타등등](#기타등등)
22 | - [네트워크](#네트워크)
23 | - [데이터베이스](#데이터베이스)
24 | - [데이터-파이프라인](#데이터-파이프라인)
25 | - [디자인패턴](#디자인패턴)
26 | - [생산성 향상 도구들](#생산성-향상-도구들)
27 | - [소프트웨어 공학](#소프트웨어-공학)
28 | - [소프트웨어 아키텍쳐](#소프트웨어-아키텍쳐)
29 | - [소프트웨어 인프라](#소프트웨어-인프라)
30 | - [알고리즘](#알고리즘)
31 | - [연구논문](#연구논문)
32 | - [자료구조](#자료구조)
33 | - [언어와 프레임워크](#언어와-프레임워크)
34 | - [운영체제](#운영체제)
35 | - [인공지능](#인공지능)
36 | - [좋은 글들](#좋은-글들)
37 | - [컴퓨터 공학](#컴퓨터-공학)
38 | - [컴퓨터 비전](#컴퓨터-비전)
39 | - [프론트 엔드](#프론트-엔드)
40 | - [유용한 사이트 정보 블로그 도구 등등](#유용한-사이트-정보-블로그-도구-등등)
41 |
42 | ## 강의
43 |
44 | - [gRPC 와 python 을 활용한 Microservice 개발기 - 송지형 - PyCon.KR 2019](https://www.youtube.com/watch?v=KGAernd-42M)
45 | - AI
46 | - [Naver Ai Boostcamp](https://blahblahlab.tistory.com/107)
47 | - [딥 러닝을 이용한 자연어 처리 입문](https://wikidocs.net/book/2155)
48 | - Airflow
49 | - [Airflow란?](https://dydwnsekd.tistory.com/27?category=897626)
50 | - Elixir
51 | - [엘릭서 스쿨(공식)](https://elixirschool.com/ko/lessons/basics/basics)
52 | - [함수형 프로그래밍 언어 : Elixir](https://www.bitzflex.com/2)
53 | - golang
54 | - [Go를 향한 여행](https://go-tour-ko.appspot.com/list)
55 | - [가장 빨리 만나는 Go 언어](http://pyrasis.com/go.html)
56 | - [예제로 배우는 Go 프로그래밍](http://golang.site/)
57 | - InfluxDB
58 | - [인플럭스DB(InfluxDB) #1 - 개요 및 특징](https://andro-jinu.tistory.com/14)
59 | - k8s
60 | - [도커와 쿠버네티스 시작하기](https://gurumee92.tistory.com/254?category=957852)
61 | - OpenCV
62 | - [OpenCV - 1. 파이썬으로 만드는 OpenCV 프로젝트](https://bkshin.tistory.com/entry/OpenCV-1-%ED%8C%8C%EC%9D%B4%EC%8D%AC%EC%9C%BC%EB%A1%9C-%EB%A7%8C%EB%93%9C%EB%8A%94-OpenCV-%ED%94%84%EB%A1%9C%EC%A0%9D%ED%8A%B8?category=1148027)
63 | - Rust
64 | - [Rust by Example](https://doc.rust-lang.org/rust-by-example/index.html)
65 | - [The Rust Programming Language(en)](https://doc.rust-lang.org/book/title-page.html)
66 | - [The Rust Programming Language(en), (quiz)](https://rust-book.cs.brown.edu/experiment-intro.html)
67 | - [The Rust Programming Language(ko)](https://rinthel.github.io/rust-lang-book-ko/foreword.html)
68 | - SE
69 | - [IT 기술 노트](https://wikidocs.net/book/2184)
70 |
71 | ## 검색
72 |
73 | - [NDCG - Normalized Discounted Cumulative Gain(평가지표)](https://walwalgabu.tistory.com/entry/4-NDCG-Normalized-Discounted-Cumulative-Gain%ED%8F%89%EA%B0%80%EC%A7%80%ED%91%9C)
74 | - [단어 임베딩: 어휘의 의미(Lexical semantics)를 인코딩하기](https://tutorials.pytorch.kr/beginner/nlp/word_embeddings_tutorial.html)
75 | - [[데이터 색인] 역색인 구조 (역 인덱스; Inverted Index)](https://the-dev.tistory.com/30)
76 |
77 | ## 기타등등
78 |
79 | - [Asynchronous Engine — (1) libuv](https://blue-hope.medium.com/asynchronous-engine-1-libuv-2508a4bebb42)
80 | - [Asynchronous Engine — (2) uvloop](https://blue-hope.medium.com/asynchronous-engine-2-uvloop-ef895d2c2b4a)
81 | - [Asynchronous Engine — (3) uvicorn](https://blue-hope.medium.com/asynchronous-engine-3-uvicorn-e52e99b61b80)
82 | - [Base64 인코딩이란?](https://effectivesquid.tistory.com/entry/Base64-%EC%9D%B8%EC%BD%94%EB%94%A9%EC%9D%B4%EB%9E%80)
83 | - [Base64이란 무엇일까? / Base64 사용 이유와 인코딩과 디코딩](https://devuna.tistory.com/41)
84 | - [Jupyter notebook 서브도메인 설정 및 Nginx https 설정 방법(certbot)](http://blog.ju-ing.com/posts/DNS-subdomain/)
85 | - [KAIST CS320 Programming Languages Course Reading Materials](https://hjaem.info/articles/main)
86 | - [NVIDIA-SMI 확인방법 및 활용하기](https://kyumdoctor.co.kr/10)
87 | - [람다 대수](https://ko.wikipedia.org/wiki/%EB%9E%8C%EB%8B%A4_%EB%8C%80%EC%88%98)
88 | - [분류 모델 성능 평가 지표(Accuracy, Precision, Recall, F1 score 등)](https://white-joy.tistory.com/9)
89 | - [[이론 및 파이썬] L1 Norm과 L2 Norm](https://hwanii-with.tistory.com/58)
90 |
91 | ## 네트워크
92 |
93 | - [AB(Apache http server Benchmarking tool)를 활용한 벤치마킹 테스트](https://sysops.tistory.com/77)
94 | - [Apache Avro 란](https://p-bear.tistory.com/48)
95 | - [AWS VPC를 디자인해보자(1) - Multi AZ와 Subnet을 활용한 고가용성](https://bluese05.tistory.com/45)
96 | - [[Firebase] FCM에 대해서 알아보자. 🔔]()
97 | - [GET과 POST의 차이](https://hongsii.github.io/2017/08/02/what-is-the-difference-get-and-post/)
98 | - [HTTP와 HTTPS의 차이점](https://dany-it.tistory.com/96)
99 | - [http와 tcp/ip의 이해](https://hwan-shell.tistory.com/271)
100 | - [HTTP Protocols](https://ko.wikipedia.org/wiki/HTTP)
101 | - [HTTP 통신 과정](https://mysterico.tistory.com/29)
102 | - [🌐 IP 클래스 · 서브넷 마스크 · 서브넷팅 계산법 💯 총정리](https://inpa.tistory.com/entry/WEB-IP-클래스-서브넷-마스크-서브넷팅-총정리)
103 | - [JWT(Json Web Token)란?](https://mangkyu.tistory.com/56)
104 | - [JSON이란?](https://ko.wikipedia.org/wiki/JSON)
105 | - [Let’s Encrypt 와일드카드로 여러개의 서브도메인 인증서 한번에 발급받기](https://oasisfores.com/letsencrypt-wildcard-ssl-certificate/)
106 | - [Let's Encrypt SSL 인증서 자동 갱신 설정 방법](https://devlog.jwgo.kr/2019/04/16/how-to-lets-encrypt-ssl-renew/)
107 | - [OAuth란? 그리고 OAuth1, OAuth2](https://minwan1.github.io/2018/02/24/2018-02-24-OAuth/)
108 | - [OAuth2를 이용한 SSO 환경 구축 (1/2)](http://www.nextree.co.kr/oauth-2reul-iyonghan-sso-hwangyeong-gucug-1-2/)
109 | - [OAuth2를 이용한 SSO 환경 구축 (2/2)](http://www.nextree.co.kr/oauth-2reul-iyonghan-sso-hwangyeong-gucug-2-2/)
110 | - [OSI 모형](https://namu.wiki/w/OSI%20%EB%AA%A8%ED%98%95)
111 | - [SSO(Single Sign-On)이란?](https://toma0912.tistory.com/75)
112 | - [TCP/IP의 이해](https://m.blog.naver.com/jhc9639/221411218450?referrerCode=1)
113 | - [TCP와 UDP의 특징 및 차이점 알아보기](https://dev-coco.tistory.com/144)
114 | - [TLS (Transport Layer Security)](https://brownbears.tistory.com/402)
115 | - [브라우저의 렌더링 과정](https://medium.com/%EA%B0%9C%EB%B0%9C%EC%9E%90%EC%9D%98%ED%92%88%EA%B2%A9/%EB%B8%8C%EB%9D%BC%EC%9A%B0%EC%A0%80%EC%9D%98-%EB%A0%8C%EB%8D%94%EB%A7%81-%EA%B3%BC%EC%A0%95-5c01c4158ce)
116 | - [실시간 스트리밍 프로토콜-RTSP(Real Time Streaming Protocol)란?](https://mingtrace.tistory.com/442)
117 | - [웹 브라우저에 URL을 입력하면 어떤 일이 일어날까?](https://owlgwang.tistory.com/1)
118 | - [웹의 동작 원리](https://velog.io/@wonhee010/%EC%9B%B9%EC%9D%98-%EB%8F%99%EC%9E%91-%EC%9B%90%EB%A6%AC)
119 | - [인증과 인가 (권한 부여) 비교 – 특징 및 차이점](https://www.okta.com/kr/identity-101/authentication-vs-authorization/)
120 | - [쿠키와 세션의 차이](https://jeong-pro.tistory.com/80)
121 | - [토근 기반 인증에서 bearer는 무엇일까?](https://velog.io/@cada/%ED%86%A0%EA%B7%BC-%EA%B8%B0%EB%B0%98-%EC%9D%B8%EC%A6%9D%EC%97%90%EC%84%9C-bearer%EB%8A%94-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C)
122 | - [프록시(proxy)란, forward proxy와 reverse proxy](https://sujinhope.github.io/2021/06/13/Network-%ED%94%84%EB%A1%9D%EC%8B%9C(Proxy)%EB%9E%80,-Forward-Proxy%EC%99%80-Reverse-Proxy.html)
123 | - GraphQL
124 | - [GraphQL 개념잡기](https://tech.kakao.com/2019/08/01/graphql-basic/)
125 | - [GraphQL이란 무엇인가요?](https://www.redhat.com/ko/topics/api/what-is-graphql)
126 | - gRPC
127 | - [Google Protobuf 정리 내용 및 사용방법](https://jins-dev.tistory.com/entry/Google-Protobuf-%EC%A0%95%EB%A6%AC-%EB%82%B4%EC%9A%A9-%EB%B0%8F-%EC%82%AC%EC%9A%A9%EB%B0%A9%EB%B2%95)
128 | - [gRPC 1 - gRPC란?](https://chacha95.github.io/2020-06-15-gRPC1/)
129 | - [python 에서 gRPC 테스트 해보기](https://kim-daeyong.github.io/2021-07-23-grpc_python/)
130 | - nginx
131 | - [nginx로 로드밸런싱 하기](https://kamang-it.tistory.com/entry/WebServernginxnginx%EB%A1%9C-%EB%A1%9C%EB%93%9C%EB%B0%B8%EB%9F%B0%EC%8B%B1-%ED%95%98%EA%B8%B0)
132 | - [nginx와 http basic auth로 사용자 인증하기](https://ghleokim.github.io/http-basic-auth%EC%97%90-%EB%8C%80%ED%95%98%EC%97%AC/)
133 | - RestAPI
134 | - [REST API 제대로 알고 사용하기](https://meetup.toast.com/posts/92)
135 | - [그놈의 RESTful API. 한 줄로 정의하자면](https://this-programmer.tistory.com/entry/%EA%B7%B8%EB%86%88%EC%9D%98-RESTful-API-%ED%95%9C-%EC%A4%84%EB%A1%9C-%EC%A0%95%EC%9D%98%ED%95%98%EC%9E%90%EB%A9%B4)
136 | - 로드밸런싱(Load Balancing)
137 | - [로드 밸런서(Load Balancer)란?](https://nesoy.github.io/articles/2018-06/Load-Balancer)
138 | - [로드밸런싱방식 종류](https://medium.com/@pakss328/%EB%A1%9C%EB%93%9C%EB%B0%B8%EB%9F%B0%EC%84%9C%EB%9E%80-l4-l7-501fd904cf05)
139 | - 프록시 서버(Proxy Server)
140 | - [프록시 서버란?(1)](https://brownbears.tistory.com/191)
141 | - [프록시 서버란?(2)](https://soul0.tistory.com/230)
142 |
143 | ## 데이터베이스
144 |
145 | - [@Transactional의 해로움](https://channel.io/ko/blog/bad-transactional)
146 | - [📋 제 1-2-3 정규화 & 역정규화 기법 💯 정리](https://inpa.tistory.com/entry/DB-%F0%9F%93%9A-%EC%A0%9C-1-2-3-%EC%A0%95%EA%B7%9C%ED%99%94-%EC%97%AD%EC%A0%95%EA%B7%9C%ED%99%94)
147 | - [#1 데이터베이스의 무결성을 보장해주는 WAL(Write-Ahead Logging)](https://bourbonkk.tistory.com/86)
148 | - [ACID vs BASE](https://velog.io/@jeb1225/ACIDvsBASE)
149 | - [ACID 데이터베이스와 BASE 데이터베이스의 차이점은 무엇인가요?](https://aws.amazon.com/ko/compare/the-difference-between-acid-and-base-database/)
150 | - [CAP theorem](https://en.wikipedia.org/wiki/CAP_theorem)
151 | - [Clustering vs Replication vs Sharding](https://jordy-torvalds.tistory.com/94)
152 | - [DB 트랜잭션 (Transaction)의 ACID 속성과 분산시스템 BASE 속성](https://velog.io/@issac/DB-%ED%8A%B8%EB%9E%9C%EC%9E%AD%EC%85%98-Transaction%EC%9D%98-ACID-%EC%86%8D%EC%84%B1%EA%B3%BC-%EB%B6%84%EC%82%B0%EC%8B%9C%EC%8A%A4%ED%85%9C-BASE-%EC%86%8D%EC%84%B1)
153 | - [[DB] SQL - JOIN문, JOIN 종류 (Inner Join,Natural Join,Outer Join,Cross Join)](https://doh-an.tistory.com/30)
154 | - [Inner Join과 Outer Join 차이점](https://server-engineer.tistory.com/306)
155 | - [Lock에 대해서 알아보자 - 기본편](https://sabarada.tistory.com/121)
156 | - [MongoDB의 Transaction과 session문제](https://crmrelease.tistory.com/138)
157 | - [ORM이란](https://gmlwjd9405.github.io/2019/02/01/orm.html)
158 | - [WAL (Write-Ahead-Logging)](https://nays111.tistory.com/12)
159 | - [데이터베이스 튜닝 (DB Tuning)](http://blog.skby.net/%EB%8D%B0%EC%9D%B4%ED%84%B0%EB%B2%A0%EC%9D%B4%EC%8A%A4-%ED%8A%9C%EB%8B%9D-db-tuning/)
160 | - [왜 데이터베이스(DB) 튜닝을 해야할까?](https://travislife.tistory.com/25)
161 | - [인덱스(index)란?](https://mangkyu.tistory.com/96)
162 | - [인덱스의 원리 및 종류](https://ssunws.tistory.com/45)
163 | - [저장 프로시저](https://ko.wikipedia.org/wiki/%EC%A0%80%EC%9E%A5_%ED%94%84%EB%A1%9C%EC%8B%9C%EC%A0%80)
164 | - [[Database] 5. 데이터베이스 프로그래밍](https://mangkyu.tistory.com/26)
165 | - [[Database] 7. 정규화(Normalization)](https://mangkyu.tistory.com/28)
166 | - [[Database] 8. 트랜잭션, 동시성 제어, 회복](https://mangkyu.tistory.com/30)
167 | - [[Database] 정규화(Normalization) 쉽게 이해하기](https://mangkyu.tistory.com/110)
168 | - [[DB] DB의 INDEX 개념정리](https://azderica.github.io/00-db-index/)
169 | - [[DB] 정규화(Normalization)란? 정규화 예시, 1NF, 2NF, 3NF, BCNF](https://code-lab1.tistory.com/48)
170 | - [Postgresql 의 MVCC, Vacuum에 대해 알아보자](https://velog.io/@on5949/Postgresql-%EC%9D%98-MVCC-Vacuum%EC%97%90-%EB%8C%80%ED%95%B4-%EC%95%8C%EC%95%84%EB%B3%B4%EC%9E%90)
171 | - [클러스터링 vs 리플리케이션 vs 샤딩](https://velog.io/@gkskaks1004/%ED%81%B4%EB%9F%AC%EC%8A%A4%ED%84%B0%EB%A7%81-vs-%EB%A6%AC%ED%94%8C%EB%A6%AC%EC%BC%80%EC%9D%B4%EC%85%98-vs-%EC%83%A4%EB%94%A9)
172 | - [클러스터드 인덱스 (Clustered Index), 넌 클러스터드 인덱스 (Non Clustered Index)](https://velog.io/@sweet_sumin/%ED%81%B4%EB%9F%AC%EC%8A%A4%ED%84%B0%EB%93%9C-%EC%9D%B8%EB%8D%B1%EC%8A%A4-Clustered-Index-%EB%84%8C-%ED%81%B4%EB%9F%AC%EC%8A%A4%ED%84%B0%EB%93%9C-%EC%9D%B8%EB%8D%B1%EC%8A%A4-Non-Clustered-Index)
173 | - [클러스터 인덱스와 넌클러스터 인덱스/ 개념 총정리](https://junghn.tistory.com/entry/DB-%ED%81%B4%EB%9F%AC%EC%8A%A4%ED%84%B0-%EC%9D%B8%EB%8D%B1%EC%8A%A4%EC%99%80-%EB%84%8C%ED%81%B4%EB%9F%AC%EC%8A%A4%ED%84%B0-%EC%9D%B8%EB%8D%B1%EC%8A%A4-%EA%B0%9C%EB%85%90-%EC%B4%9D%EC%A0%95%EB%A6%AC)
174 | - [테이블 조인 종류(Table Join Type)](https://sparkdia.tistory.com/17)
175 | - [트랜잭션 격리 수준(Transaction Isolation Level)](https://dar0m.tistory.com/225)
176 | - [트랜잭션이란? (Transaction)](https://limkydev.tistory.com/100?category=974039)
177 | - [트랜잭션과 격리성](https://sabarada.tistory.com/117)
178 | - [트랜잭션(transaction)이란?(1)](https://mommoo.tistory.com/62)
179 | - [트랜잭션(transaction)이란?(2)](https://devuna.tistory.com/30)
180 | - [트리거(Trigger)란?](https://limkydev.tistory.com/154)
181 | - [효과적인 DB index 설정하기](https://velog.io/@jwpark06/%ED%9A%A8%EA%B3%BC%EC%A0%81%EC%9D%B8-DB-index-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0)
182 | - ElasticSearch
183 | - [CRUD - 입력, 조회, 수정, 삭제](https://esbook.kimjmin.net/04-data/4.2-crud)
184 | - [EFK Stack 구성](http://www.iorchard.net/2019/06/17/efk_stack_%EA%B5%AC%EC%84%B1.html)
185 | - [ELK Stack 이란? 소개, 정의](https://velog.io/@holidenty/ELK-ELK-Stack-%EC%9D%B4%EB%9E%80-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C)
186 | - [Elasticsearch-Kibana를 이용한 로그 모니터링 (1)](https://gintrie.tistory.com/45?category=389204)
187 | - [[Elastic Search] 기본 개념과 특징(장단점)](https://jaemunbro.medium.com/elastic-search-%EA%B8%B0%EC%B4%88-%EC%8A%A4%ED%84%B0%EB%94%94-ff01870094f0)
188 | - [Elasticsearch에 fluentd를 얹은 EFK stack 구축하기(with kubernetes)](https://nangman14.tistory.com/68)
189 | - [ELK 스택](https://aws.amazon.com/ko/opensearch-service/the-elk-stack/)
190 | - [Elasticsearch란? (개념 및 종류, RDBMS와 차이)](https://choseongho93.tistory.com/231)
191 | - [fuzzy 알고리즘 (무엇을 찾고 있는가?)](https://knight76.tistory.com/entry/elasticsearch-fuzzy-%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98-%EB%AC%B4%EC%97%87%EC%9D%84-%EC%B0%BE%EA%B3%A0-%EC%9E%88%EB%8A%94%EA%B0%80)
192 | - [Using ElasticSearch, Fluentd and Kibana (for log aggregation)](https://technology.amis.nl/continuous-delivery/containers/using-elasticsearch-fluentd-and-kibana-for-log-aggregation/)
193 | - [Field data types](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-types.html)
194 | - [macOS에서 ELK stack 구성하기 (elasticsearch)](https://this-programmer.tistory.com/476)
195 | - [엘라스틱서치로 파이썬(Python) 어플의 구조화 로깅(Structured Logging) 구현하기 (1)](https://blog.naver.com/olpaemi/221967869387)
196 | - [엘라스틱서치와 추천 - More Like This 쿼리](https://onduway.tistory.com/101)
197 | - MySQL
198 | - [How to bind MySQL server to more than one IP address?](https://serverfault.com/questions/139323/how-to-bind-mysql-server-to-more-than-one-ip-address)
199 | - [[MYSQL] 📚 인덱스(index) 핵심 설계 & 사용 문법 💯 총정리](https://inpa.tistory.com/entry/MYSQL-%F0%9F%93%9A-%EC%9D%B8%EB%8D%B1%EC%8A%A4index-%ED%95%B5%EC%8B%AC-%EC%84%A4%EA%B3%84-%EC%82%AC%EC%9A%A9-%EB%AC%B8%EB%B2%95-%F0%9F%92%AF-%EC%B4%9D%EC%A0%95%EB%A6%AC)
200 | - MongoDB
201 | - [[MongoDB] 몽고DB 샤딩(Sharding) 구성하기!](https://tmjb.tistory.com/39)
202 | - [[ MongoDB ] 샤딩(Sharding)이란?](https://dev-cini.tistory.com/36)
203 | - [[ MongoDB ] 샤딩 (Sharding)시스템 구성 실습](https://dev-cini.tistory.com/37)
204 | - [[몽고DB 완벽가이드] 샤딩의 개념](https://devfunny.tistory.com/907)
205 | - Telegraf
206 | - [How to Use Custom Telemetry From Telegraf in New Relic One](https://newrelic.com/blog/how-to-relic/how-to-collect-telegraf-metrics)
207 | - [Telegraf input plugins](https://docs.influxdata.com/telegraf/v1.9/plugins/inputs/)
208 | - Postgresql
209 | - [Don't Do This](https://wiki.postgresql.org/wiki/Don't_Do_This)
210 | - [Postgresql DB의 인덱싱 알고리즘](https://tre2man.tistory.com/278)
211 | - [PostgreSQL Vacuum에 대한 거의 모든 것](https://techblog.woowahan.com/9478/)
212 | - [PostgreSQL 튜닝 - Autovacuum 최적화에 대하여](https://nrise.github.io/posts/postgresql-autovacuum/)
213 | - Redis
214 | - [[Redis] ZSet 자료구조 개요](https://bugoverdose.github.io/development/redis-zset-basics/)
215 |
216 | ## 데이터-파이프라인
217 |
218 | - [데이터 파이프라인이란 무엇인가?](https://blog.voidmainvoid.net/265)
219 | - [데이터 파이프라인이란, ETL과 ELT](데이터 파이프라인이란, ETL과 ELT)
220 | - [코드 작성 없이 데이터 파이프라인 운영하기](https://blog.mathpresso.com/%EC%BD%94%EB%93%9C-%EC%9E%91%EC%84%B1-%EC%97%86%EC%9D%B4-%EB%B0%B0%EC%B9%98-%ED%8C%8C%EC%9D%B4%ED%94%84%EB%9D%BC%EC%9D%B8-%EC%9A%B4%EC%98%81%ED%95%98%EA%B8%B0-84769d598674)
221 | - [하둡(hadoop)과 스파크(Spark)](https://velog.io/@cha-suyeon/%ED%95%98%EB%91%A1hadoop%EA%B3%BC-%EC%8A%A4%ED%8C%8C%ED%81%ACSpark)
222 | - [하둡(hadoop)의 MapReduce](https://velog.io/@kimdukbae/MapReduce)
223 | - Airflow
224 | - [airflow에서 각종 operator로 분기처리하기 (feat. SimpleHttpOperator)](https://this-programmer.tistory.com/499)
225 | - [Airflow와 함께한 데이터 환경 구축기(feat. Airflow on Kubernetes)](https://tech.socarcorp.kr/data/2021/06/01/data-engineering-with-airflow.html)
226 | - [Airflow란?](https://velog.io/@jjongbumeee/Airflow1)
227 | - [Airflow vs. Kubeflow](https://velog.io/@rhee519/airflow-vs-kubeflow)
228 | - [Airflow Xcom 사용하기](https://dydwnsekd.tistory.com/107)
229 | - [Apache 에어플로우(Airflow) 시작하기 - Airflow란?](https://lsjsj92.tistory.com/631)
230 | - [DAG가 뭔가요?](https://bossm0n5t3r.github.io/posts/71/)
231 | - [Helm Chart for Apache Airflow](https://airflow.apache.org/docs/helm-chart/stable/index.html)
232 | - [How to run conditional task in Airflow with previous http operator requested value](https://stackoverflow.com/questions/57097620/how-to-run-conditional-task-in-airflow-with-previous-http-operator-requested-val)
233 | - [Kubeflow vs Airflow – Which is Better For Your Business: 4 Critical Differences](https://hevodata.com/learn/kubeflow-vs-airflow/)
234 | - [Kubernetes를 이용한 효율적인 데이터 엔지니어링(Airflow on Kubernetes VS Airflow Kubernetes Executor) – 1](https://engineering.linecorp.com/ko/blog/data-engineering-with-airflow-k8s-1/)
235 | - [Kubernetes를 이용한 효율적인 데이터 엔지니어링(Airflow on Kubernetes VS Airflow Kubernetes Executor) – 2](https://engineering.linecorp.com/ko/blog/data-engineering-with-airflow-k8s-2/)
236 | - [SimpleHTTPOperator in Apache Airflow](https://dzone.com/articles/simplehttpoperator-in-apache-airflow)
237 | - [에어플로우 시작하기: 개념 및 설치](https://data-engineer-tech.tistory.com/30)
238 | - Kubeflow
239 | - [Airflow vs. Kubeflow](https://velog.io/@rhee519/airflow-vs-kubeflow)
240 | - [Kubeflow vs Airflow – Which is Better For Your Business: 4 Critical Differences](https://hevodata.com/learn/kubeflow-vs-airflow/)
241 | - PySpark
242 | - [[pyspark/빅데이터기초] Parquet(파케이) 파일 형식이란?](https://butter-shower.tistory.com/245)
243 |
244 | ## 디자인패턴
245 |
246 | - [Design Patterns on python](https://brownbears.tistory.com/category/%EA%B3%B5%EB%B6%80/%EB%94%94%EC%9E%90%EC%9D%B8%20%ED%8C%A8%ED%84%B4)
247 | - [Monorepo? Yarn Workspace!](https://medium.com/@deptno/monorepo-yarn-workspace-e81e3e078100)
248 | - [MVC패턴이란](https://m.blog.naver.com/jhc9639/220967034588)
249 | - [디자인 패턴들 (Refactoring guru)](https://refactoring.guru/ko/design-patterns)
250 |
251 | ## 생산성 향상 도구들
252 |
253 | - [ERD CLOUD](https://www.erdcloud.com/)
254 | - [gitstar-ranking(깃허브 별 개수 랭킹 알려주는 사이트)](https://gitstar-ranking.com)
255 | - [Graphviz 소개](https://narusas.github.io/2019/01/25/Graphviz.html)
256 | - [JSON to YAML](https://www.json2yaml.com/)
257 | - [POSTMAN과 JSON Placeholder(JSON을 테스트하는 가장 좋은 방법)](https://this-programmer.tistory.com/entry/JSON%EC%9D%84-%ED%85%8C%EC%8A%A4%ED%8A%B8%ED%95%98%EB%8A%94-%EA%B0%80%EC%9E%A5-%EC%A2%8B%EC%9D%80-%EB%B0%A9%EB%B2%95-POSTMAN%EA%B3%BC-JSON-Placeholder?category=767889)
258 | - [Python용 AWS SDK(Boto3)](https://aws.amazon.com/ko/sdk-for-python/)
259 | - [regex101.com(정규식 짤 때 도움되는 사이트)](https://this-programmer.tistory.com/entry/%EC%A0%95%EA%B7%9C%EC%8B%9D-%EC%A7%A4-%EB%95%8C-%EC%97%84%EC%B2%AD%EB%82%98%EA%B2%8C-%EB%8F%84%EC%9B%80%EC%9D%B4-%EB%90%98%EB%8A%94-%EC%82%AC%EC%9D%B4%ED%8A%B8-regex101com?category=772368)
260 | - [Wappalyzer(웹사이트 구성요소를 볼 수 있는 크롬 확장 프로그램)](https://this-programmer.tistory.com/entry/%EC%9B%B9%EC%82%AC%EC%9D%B4%ED%8A%B8%EB%A5%BC-%EB%AD%98%EB%A1%9C-%EB%A7%8C%EB%93%A4%EC%97%88%EB%8A%94%EC%A7%80-%EC%95%8C-%EC%88%98-%EC%9E%88%EA%B2%8C-%ED%95%B4%EC%A3%BC%EB%8A%94-%ED%81%AC%EB%A1%AC-%ED%99%95%EC%9E%A5-%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%A8-Wappalyzer?category=772368)
261 | - [무료 DB Tool (DBeaver)](https://m.blog.naver.com/skykbc/221426494422)
262 |
263 | ## 소프트웨어 공학
264 |
265 | - [10분 Actor Model 정리](https://hyojabal.tistory.com/1)
266 | - [Active Record VS Data Mapper](https://velog.io/@hyob/Active-Record-VS-Data-Mapper)
267 | - [Actor model 에 관하여…](https://pegasuskim.wordpress.com/2015/12/23/actor-model-%EC%97%90-%EA%B4%80%ED%95%98%EC%97%AC/)
268 | - [Call by Value와 Call by Reference](https://re-build.tistory.com/3)
269 | - [Coroutine과 Subroutine의 차이](https://kotlinworld.com/214)
270 | - [Coroutine은 어떻게 스레드 작업을 최적화 하는가?](https://kotlinworld.com/139)
271 | - [Coroutine 기초](https://medium.com/@sunminlee89/%EC%BD%94%ED%8B%80%EB%A6%B0-%EC%BD%94%EB%A3%A8%ED%8B%B4-coroutine-%EA%B8%B0%EC%B4%88-1342ae6916ce)
272 | - [Dependency injection and inversion of control in Python](https://python-dependency-injector.ets-labs.org/introduction/di_in_python.html)
273 | - [IoC, DI, DIP 개념 잡기](https://vagabond95.me/posts/about-ioc-dip-di/)
274 | - [What is the difference between JMP and CALL?](https://www.quora.com/What-is-the-difference-between-JMP-and-CALL)
275 | - [고가용성](https://ko.wikipedia.org/wiki/%EA%B3%A0%EA%B0%80%EC%9A%A9%EC%84%B1)
276 | - [객체지향 설계 5원칙 - SOLID란 무엇일까?](https://devlog-wjdrbs96.tistory.com/380)
277 | - [단위 테스트 vs 통합 테스트 vs 인수 테스트](https://tecoble.techcourse.co.kr/post/2021-05-25-unit-test-vs-integration-test-vs-acceptance-test/)
278 | - [데몬 (컴퓨팅)](https://ko.wikipedia.org/wiki/%EB%8D%B0%EB%AA%AC_(%EC%BB%B4%ED%93%A8%ED%8C%85))
279 | - [동시성(Concurrency) vs 병렬성(Parallelism)](https://seamless.tistory.com/42)
280 | - [명령형 프로그래밍 VS 선언형 프로그래밍](https://boxfoxs.tistory.com/430)
281 | - [무슨 값들을 상수(constant)로 지정해야할까?](https://this-programmer.tistory.com/492)
282 | - [믹스인(Mixin)](https://ko.wikipedia.org/wiki/%EB%AF%B9%EC%8A%A4%EC%9D%B8)
283 | - [장애 허용 시스템](https://ko.wikipedia.org/wiki/%EC%9E%A5%EC%95%A0_%ED%97%88%EC%9A%A9_%EC%8B%9C%EC%8A%A4%ED%85%9C)
284 | - [클로저(Closure)](https://ko.wikipedia.org/wiki/%ED%81%B4%EB%A1%9C%EC%A0%80_(%EC%BB%B4%ED%93%A8%ED%84%B0_%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%B0%8D))
285 | - [『프로그래밍 언어 속 타입』(가제) 책 소개](https://blog.hjaem.info/2)
286 | - [프로그램과 프로세스와 스레드의 차이](https://velog.io/@raejoonee/%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4%EC%99%80-%EC%8A%A4%EB%A0%88%EB%93%9C%EC%9D%98-%EC%B0%A8%EC%9D%B4)
287 | - [프로세스 격리란 무엇입니까?](https://www.netinbag.com/ko/internet/what-is-process-isolation.html)
288 | - [함수(function)와 메소드(method)의 차이](https://this-programmer.tistory.com/entry/%ED%95%A8%EC%88%98Function%EC%99%80-%EB%A9%94%EC%86%8C%EB%93%9CMethod%EC%9D%98-%EC%B0%A8%EC%9D%B4)
289 | - 리액티브 프로그래밍(Reactive Programming)
290 | - [Reactive Programming 101 : 리액티브 프로그래밍이 뭔가요](https://juneyr.dev/reactive-programming)
291 | - [ReactiveX](https://reactivex.io/)
292 | - [[RxPy] Reactive Programming? Rx? 그게뭐야?]()
293 | - [리액티브 프로그래밍 (Reactive Programming) RxJava](https://coding-food-court.tistory.com/136)
294 | - [사용하면서 알게 된 Reactor, 예제 코드로 살펴보기](https://tech.kakao.com/2018/05/29/reactor-programming/)
295 | - [왕초보를 위한 ](https://zeddios.tistory.com/m/303)
296 | - 함수형 프로그래밍(Functional Programming)
297 | - [클로저(closure)란 무엇인가 (clojure 아님. Feat. Python)](https://this-programmer.tistory.com/510)
298 | - [Category Theory for Programmers: The Preface](https://bartoszmilewski.com/2014/10/28/category-theory-for-programmers-the-preface/)
299 | - [[JavaScript] - 커링에 대해 알아보자]()
300 | - [Functor란 무엇인가?](https://kpug.github.io/fp-gitbook/Chapter4.html)
301 | - [Monad란 무엇인가?](https://kpug.github.io/fp-gitbook/Chapter5.html)
302 | - [Monoid란 무엇인가?](https://kpug.github.io/fp-gitbook/Chapter3.html)
303 | - [모나드와 함수형 아키텍처](https://teamdable.github.io/techblog/Moand-and-Functional-Architecture)
304 | - [함수형 프로그래밍(Functional Programming) 이란?](https://mangkyu.tistory.com/111)
305 | - [함수형 프로그래밍 요약](https://velog.io/@kyusung/%ED%95%A8%EC%88%98%ED%98%95-%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%B0%8D-%EC%9A%94%EC%95%BD)
306 |
307 | ## 소프트웨어 아키텍쳐
308 |
309 | - [Architectural Katas](https://www.architecturalkatas.com/index.html)
310 | - [Architectural Katas - neal ford](https://nealford.com/katas/)
311 | - [connascence.io/](https://connascence.io/)
312 | - [MSA 기반 환경에서의 인증과 인가 - 1. 개요](https://devs0n.tistory.com/26)
313 | - [Observability vs Monitoring 차이점은 무엇일까요?](https://blog.stkcorp.co.kr/splunk/observability-vs-monitoring-%EC%B0%A8%EC%9D%B4%EC%A0%90%EC%9D%80-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C%EC%9A%94)
314 | - [Patterns for Building LLM-based Systems & Products](https://eugeneyan.com/writing/llm-patterns/)
315 | - [System Design: The complete course](https://kps.hashnode.dev/system-design-the-complete-course)
316 | - [What Is a Modular Monolith?](https://www.milanjovanovic.tech/blog/what-is-a-modular-monolith)
317 | - [계층구조(Hierarchy)](https://m.blog.naver.com/PostView.naver?isHttpsRedirect=true&blogId=sipack7297&logNo=220427434575)
318 | - [🌍 레이어드 아키텍쳐](https://velog.io/@may_soouu/%EB%A0%88%EC%9D%B4%EC%96%B4%EB%93%9C-%EC%95%84%ED%82%A4%ED%85%8D%EC%B3%90)
319 | - [분산 시스템이란?](https://www.atlassian.com/ko/microservices/microservices-architecture/distributed-architecture)
320 | - [헥사고날 아키텍처란](https://cantcoding.tistory.com/107)
321 |
322 | ## 소프트웨어 인프라
323 |
324 | - [(Almost) Every infrastructure decision I endorse or regret after 4 years running infrastructure at a startup](https://cep.dev/posts/every-infrastructure-decision-i-endorse-or-regret-after-4-years-running-infrastructure-at-a-startup/)
325 | - [ArgoCD 정리 (1) - GitOps Repo 구성과 ArgoCD 설치](https://asuraiv.tistory.com/20)
326 | - [[CEPH] Ceph Architecture](https://chhanz.github.io/ceph/2021/08/18/ceph-architecture/)
327 | - [datadog integrations](https://docs.datadoghq.com/integrations/#all)
328 | - [devops란 - from aws](https://aws.amazon.com/ko/devops/what-is-devops/)
329 | - [Failover, 페일오버란 무엇인가](https://m.blog.naver.com/on21life/221221178100)
330 | - [Flapping in Autoscale](https://learn.microsoft.com/en-us/azure/azure-monitor/autoscale/autoscale-flapping)
331 | - [GlusterFS basic](https://gruuuuu.github.io/linux/glusterfs/)
332 | - [Hot key Cache Stampede와 Probabilistic Early Recomputation 적용](https://velog.io/@xogml951/Hot-key%EC%97%90%EC%84%9C-Cache-Stampede%EC%99%80-Probabilistic-Early-Recomputation-%EC%A0%81%EC%9A%A9)
333 | - [How to do version control in Machine Learning projects](https://pyaf.medium.com/how-to-do-version-control-in-machine-learning-projects-2d693510efcf)
334 | - [monorepo.tools](https://monorepo.tools/)
335 | - [Nexus3를 이용한 pypi 사설 저장소 구축](https://www.bearpooh.com/45)
336 | - [Sentry.io 에러 로깅](https://woolbro.tistory.com/93)
337 | - [TBD(Trunk Based Development) 전략이란?](https://helloinyong.tistory.com/335)
338 | - [[Telegraf + influxDB + Grafana]10분만에 데브옵스를 위한 모니터링 시스템 구축하기](https://blog.voidmainvoid.net/91)
339 | - [TICK Stack(Telegraf + InfluxDB + Chronograf + Kapacitor)](https://notemusic.tistory.com/67)
340 | - [Trunk Based Development](https://trunkbaseddevelopment.com/)
341 | - [마이크로서비스 인증/인가 패턴](https://engineering-skcc.github.io/microservice%20outer%20achitecture/outer-arch-Auth/)
342 | - [배포 방법 정리 (고정/롤링/블루-그린/카나리 릴리즈 배포)](https://devpouch.tistory.com/136)
343 | - [안정적인 운영을 완성하는 모니터링, 프로메테우스와 그라파나](https://velog.io/@moey920/%EC%95%88%EC%A0%95%EC%A0%81%EC%9D%B8-%EC%9A%B4%EC%98%81%EC%9D%84-%EC%99%84%EC%84%B1%ED%95%98%EB%8A%94-%EB%AA%A8%EB%8B%88%ED%84%B0%EB%A7%81.-%ED%94%84%EB%A1%9C%EB%A9%94%ED%85%8C%EC%9A%B0%EC%8A%A4%EC%99%80-%EA%B7%B8%EB%9D%BC%ED%8C%8C%EB%82%98)
344 | - [엣시와 콘웨이 법칙 - 데브옵스 핸드북 읽기](https://brunch.co.kr/@moonjoonyoung/6)
345 | - [오케스트레이션(Orchestration)이란?](https://www.redhat.com/ko/topics/automation/what-is-orchestration)
346 | - [장애 대응 능력을 확인할 수 있는 지표 MTTD/MTTR/MTTF/MTBF](https://www.whatap.io/bbs/board.php?bo_table=blog&wr_id=220)
347 | - [코드형 인프라(IaC)란?](https://www.redhat.com/ko/topics/automation/what-is-infrastructure-as-code-iac)
348 | - [페일오버(Failover)란 무엇인가](https://oriyong.tistory.com/80)
349 | - ['폴리리포주의자'가 모노리포를 반대하는 3가지 이유](https://www.itworld.co.kr/insight/214234)
350 | - [프로비저닝(Provisioning)이란? 개념, 종류, 자동화 방법](https://www.redhat.com/ko/topics/automation/what-is-provisioning)
351 | - [현기증나는 인프라, 배포 용어들(IaC, 오케스트레이션, CI/CD, DEVOPS, 프로비저닝 등등) 정리](https://this-programmer.tistory.com/447)
352 | - AWS
353 | - [AWS | ALB와 NLB 차이점](https://no-easy-dev.tistory.com/entry/AWS-ALB%EC%99%80-NLB-%EC%B0%A8%EC%9D%B4%EC%A0%90)
354 | - [ACM을 이용한 HTTPS 설정](https://intermediate.inflearn.devopsart.dev/2./acm-https)
355 | - [aws 프리티어 계속 쓰기 (with gmail)](https://this-programmer.tistory.com/472)
356 | - [[AWS] ACM + Route53을 이용한 SSL(Https) 인증서 발급]()
357 | - [[AWS] 가장쉽게 VPC 개념잡기](https://medium.com/harrythegreat/aws-%EA%B0%80%EC%9E%A5%EC%89%BD%EA%B2%8C-vpc-%EA%B0%9C%EB%85%90%EC%9E%A1%EA%B8%B0-71eef95a7098)
358 | - [CloudWatch 에이전트를 사용하여 Amazon EC2 인스턴스 및 온프레미스 서버에서 지표 및 로그 수집](https://docs.aws.amazon.com/ko_kr/AmazonCloudWatch/latest/monitoring/Install-CloudWatch-Agent.html)
359 | - [Mac OS에 AWS Cli 설정하기](https://longtermsad.tistory.com/13)
360 | - CircleCI
361 | - [CircleCI 맛보기](https://velog.io/@priveate/CircleCI-%EB%A7%9B%EB%B3%B4%EA%B8%B0)
362 | - Docker
363 | - [Docker container가 localhost를 볼 수 있게 하는 방법](https://this-programmer.tistory.com/494)
364 | - [docker, cronjob 하는 container 만들기 + supervisor, 환경변수 적용하기](https://this-programmer.tistory.com/488)
365 | - [From inside of a Docker container, how do I connect to the localhost of the machine?](https://stackoverflow.com/questions/24319662/from-inside-of-a-docker-container-how-do-i-connect-to-the-localhost-of-the-mach)
366 | - [Podman 소개](https://dejavuhyo.github.io/posts/podman/)
367 | - [RUN, CMD, ENTRYPOINT 차이점](https://seokhyun2.tistory.com/61)
368 | - [도커 컨테이너는 가상머신인가요? 프로세스인가요?](https://www.44bits.io/ko/post/is-docker-container-a-virtual-machine-or-a-process)
369 | - [도커(Docker)로 CentOS 이미지 systemctl 사용하기](https://this-programmer.tistory.com/entry/%EB%8F%84%EC%BB%A4Docker%EB%A1%9C-CentOS-%EC%9D%B4%EB%AF%B8%EC%A7%80-systemctl-%EC%82%AC%EC%9A%A9%ED%95%98%EA%B8%B0-2-failed-to-get-DBus-connection-Operation-not-permitted)
370 | - [초보를 위한 도커 안내서 - 도커란 무엇인가?](https://subicura.com/2017/01/19/docker-guide-for-beginners-1.html)
371 | - Debezium
372 | - [Debezium이란?](https://gunju-ko.github.io/kafka/2020/06/18/Debezium.html)
373 | - DVC (Data Version Control)
374 | - [DVC - (1) Data Management](https://dong-life.tistory.com/33)
375 | - [DVC(Data Version Control) with Docker](https://visionhong.tistory.com/37?category=946471)
376 | - [DVC(Data Version Control) 소개](https://devocean.sk.com/blog/techBoardDetail.do?ID=163379)
377 | - [The ultimate guide to building maintainable Machine Learning pipelines using DVC](https://towardsdatascience.com/the-ultimate-guide-to-building-maintainable-machine-learning-pipelines-using-dvc-a976907b2a1b)
378 | - [Versioning data and models in ML projects using DVC and AWS S3](https://medium.com/analytics-vidhya/versioning-data-and-models-in-ml-projects-using-dvc-and-aws-s3-286e664a7209)
379 | - FluentD
380 | - [Fluentd(td-agent) 설치 및 실행 방법](https://jangseongwoo.github.io/fluentd/fluentd_install/)
381 | - [Fluentd + Elasticsearch + Kibana EFK Stack 구축하기](https://smoh.tistory.com/415)
382 | - [Fluentd(td-agent) output plugin](https://jangseongwoo.github.io/fluentd/fluentd_output_plugin_operation_check/)
383 | - [FluentD 설치 및 실행 방법](https://jinseongsoft.tistory.com/339)
384 | - [Fluentd란?](https://velog.io/@seho100/Fluentd%EB%9E%80)
385 | - [Fluentd란 무엇인가? 구조와 기능 살펴보기](https://jonnung.dev/system/2018/04/06/fluentd-log-collector-part1/)
386 | - [[Fluentd]를 이용한 로그 수집 -1.Fluentd란?]()
387 | - [Fluentd 와 LogStash 비교](https://grip.news/archives/1340)
388 | - [Fluentd 의 활용. ElasticSearch, Kibana 을 사용한 Nginx Log 수집](https://grip.news/archives/1344)
389 | - [Kubernetes 에서 fluentd + elasticsearch 연동하기](https://ksr930.tistory.com/146)
390 | - [로그 수집 패턴, Fluentd 개념 정리](https://nyyang.tistory.com/120)
391 | - Git
392 | - [django로 github actions찍먹해보기](https://this-programmer.tistory.com/474)
393 | - [Git Flow란, 깃 브랜치 전략](https://puleugo.tistory.com/107)
394 | - [Github Action 사용법 정리](https://zzsza.github.io/development/2020/06/06/github-action/)
395 | - [github actions로 자동 1일 1커밋 봇 만들기](https://this-programmer.tistory.com/490)
396 | - [Github Action을 마켓에 등록해보자](https://medium.com/jung-han/github-action%EC%9D%84-%EB%A7%88%EC%BC%93%EC%97%90-%EB%93%B1%EB%A1%9D%ED%95%B4%EB%B3%B4%EC%9E%90-7a181a0b4a8f)
397 | - [Github Action을 이용한 CI/CD 개발 주기 자동화](https://velog.io/@youngerjesus/Github-Action%EC%9D%84-%EC%9D%B4%EC%9A%A9%ED%95%9C-CICD-%EA%B0%9C%EB%B0%9C-%EC%A3%BC%EA%B8%B0-%EC%9E%90%EB%8F%99%ED%99%94)
398 | - [github actions의 자세한 실행환경 + 요청 IP 알아보기](https://this-programmer.tistory.com/498)
399 | - [Git Rebase & Squash](https://velog.io/@ppl8709/git-rebase)
400 | - [Github Action 빠르게 시작하기](https://jonnung.dev/devops/2020/01/31/github_action_getting_started/)
401 | - [Github Action에 대한 소개와 사용법](https://velog.io/@ggong/Github-Action%EC%97%90-%EB%8C%80%ED%95%9C-%EC%86%8C%EA%B0%9C%EC%99%80-%EC%82%AC%EC%9A%A9%EB%B2%95)
402 | - [Github에 push시 Jenkins Webhook 연동 방법](https://medium.com/hgmin/jenkins-github-webhook-3dc13efd2437)
403 | - [Github에 잘못 올라간 파일 삭제하기](https://gmlwjd9405.github.io/2018/05/17/git-delete-incorrect-files.html)
404 | - [[Git] Merge 이해하기 (Merge / Squash and Merge / Rebase and Merge)]()
405 | - [pre-commit 도구로 Git Hook 사용하기](https://www.daleseo.com/pre-commit/)
406 | - [맥북에서 GitHub 계정 여러개 사용하는 방법!](https://somjang.tistory.com/entry/%EB%A7%A5%EB%B6%81%EC%97%90%EC%84%9C-GitHub-%EA%B3%84%EC%A0%95-%EC%97%AC%EB%9F%AC%EA%B0%9C-%EC%82%AC%EC%9A%A9%ED%95%98%EB%8A%94-%EB%B0%A9%EB%B2%95)
407 | - [우린 Git-flow를 사용하고 있어요](https://techblog.woowahan.com/2553/)
408 | - [전역 gitignore 설정하기](https://gomjellie.github.io/git/2017/06/15/global-git-ignore.html)
409 | - [좋은 git 커밋 메시지를 작성하기 위한 7가지 약속](https://meetup.toast.com/posts/106)
410 | - [초심자를 위한 Github 협업 튜토리얼 (with 토끼와 거북이)](https://milooy.wordpress.com/2017/06/21/working-together-with-github-tutorial/)
411 | - [훅으로 Git에 훅 들어가기](https://techblog.woowahan.com/2530/)
412 | - Gitops
413 | - [GitOps and Kubernetes](https://kangwoo.kr/2019/12/18/gitops-and-kubernetes/)
414 | - [GitOps란?](https://www.redhat.com/ko/topics/devops/what-is-gitops)
415 | - [GipOps와 ArgoCD란?](https://gruuuuu.github.io/cloud/argocd-gitops/)
416 | - Jenkins
417 | - [Git 연동하기(Git Token 발급 + Jenkins Credential 등록)](https://velog.io/@zzarbttoo/JenkinsGit-%EC%97%B0https://velog.io/@jay2u8809/Crontab%ED%81%AC%EB%A1%A0%ED%83%AD-%EC%8B%9C%EA%B0%84-%EC%84%A4%EC%A0%95%EB%8F%99%ED%95%98%EA%B8%B0Git-Token-%EB%B0%9C%EA%B8%89-Jenkins-Credential-%EB%93%B1%EB%A1%9D)
418 | - [Git과 연동하기](https://yeonyeon.tistory.com/58)
419 | - [Jenkins와 github 연동하기](https://goddaehee.tistory.com/258)
420 | - [Jenkins와 Github로 CI 구성하기(Blue Ocean)](https://velog.io/@solchan/Jenkins-Jenkins%EC%99%80-Github%EB%A1%9C-CI-%EA%B5%AC%EC%84%B1%ED%95%98%EA%B8%B0)
421 | - [Mac 에서 Jenkins 설치하기](https://wan-blog.tistory.com/74)
422 | - [젠킨스란 무엇인가](https://ict-nroo.tistory.com/31)
423 | - Kafka
424 | - [[Apache kafka 조금 아는 척하기] 카프카란?]()
425 | - [[Apache Kafka] 카프카 컨슈머(Consumer)의 파티션과 메시지 순서를 알아보자 [2]](https://firststep-de.tistory.com/39)
426 | - [Apache Kafka 주요 개념 정리 (Cluster, Topic, Producer, Consumer)](https://wildeveloperetrain.tistory.com/225)
427 | - [Error Handling Patterns for Apache Kafka Applications](https://www.confluent.io/blog/error-handling-patterns-in-kafka/)
428 | - [Introducing ksqlDB](https://devidea.tistory.com/73)
429 | - [LINE에서 Kafka를 사용하는 방법 – 1편](https://engineering.linecorp.com/ko/blog/how-to-use-kafka-in-line-1/)
430 | - [Kafka Introduction](https://kafka.apache.org/intro)
431 | - [[Kafka 101] 스키마 레지스트리 (Schema Registry)](https://always-kimkim.tistory.com/entry/kafka101-schema-registry)
432 | - [[Kafka 101] 컨슈머 그룹 리밸런싱 (Consumer Group Rebalance)](https://always-kimkim.tistory.com/entry/kafka101-consumer-rebalance)
433 | - [[kafka] 카프카 컨슈머 그룹(consumer group) 이해하기](https://jhleed.tistory.com/180)
434 | - [Kafka Manager (CMAK)](https://server-engineer.tistory.com/759)
435 | - [Kafka란?](https://galid1.tistory.com/793)
436 | - [Kafka 스트림 처리 : ksqlDB로 양말 분류](https://ichi.pro/ko/kafka-seuteulim-cheoli-ksqldblo-yangmal-bunlyu-250788691961603)
437 | - [KSQL](https://www.confluent.io/ko-kr/product/ksql/)
438 | - [Mac에 카프카 설치하고 실행해보기!](https://somjang.tistory.com/entry/Kafka-Mac%EC%97%90-%EC%B9%B4%ED%94%84%EC%B9%B4-%EC%84%A4%EC%B9%98%ED%95%98%EA%B3%A0-%EC%8B%A4%ED%96%89%ED%95%B4%EB%B3%B4%EA%B8%B0)
439 | - [카프카 커넥트 효율적으로 관리하기](https://medium.com/@daisy_kim/%EC%B9%B4%ED%94%84%EC%B9%B4-%EC%BB%A4%EB%84%A5%ED%8A%B8-%ED%9A%A8%EC%9C%A8%EC%A0%81%EC%9C%BC%EB%A1%9C-%EA%B4%80%EB%A6%AC%ED%95%98%EA%B8%B0-8ff72f69be9d)
440 | - [카프카 컨슈머 그룹 리밸런싱 (Kafka Consumer Group Rebalancing)](https://techblog.gccompany.co.kr/%EC%B9%B4%ED%94%84%EC%B9%B4-%EC%BB%A8%EC%8A%88%EB%A8%B8-%EA%B7%B8%EB%A3%B9-%EB%A6%AC%EB%B0%B8%EB%9F%B0%EC%8B%B1-kafka-consumer-group-rebalancing-5d3e3b916c9e)
441 | - Kubernetes, k8s
442 | - [Amazon EKS 30분만에 구성하기 (CloudFormation)](https://waspro.tistory.com/651)
443 | - [Affinity & NodeSelector 사용하기](https://aws-diary.tistory.com/123)
444 | - [AWS에 kops로 쿠버네티스 클러스터 구축하기](https://twofootdog.tistory.com/43#:~:text=1.%20kops%EB%9E%80%20%EB%AC%B4%EC%97%87%EC%9D%B8%EA%B0%80,%EC%82%AD%EC%A0%9C%ED%95%A0%20%EC%88%98%20%EC%9E%88%EB%8F%84%EB%A1%9D%20%EC%A7%80%EC%9B%90%ED%95%9C%EB%8B%A4.)
445 | - [Calico CNI 동작원리 이해하기](https://velog.io/@200ok/Kubernetes-Calico-CNI-%EC%9D%B4%ED%95%B4%ED%95%98%EA%B8%B0)
446 | - [Calico?Weave? CNI에 관하여](https://ykarma1996.tistory.com/179)
447 | - [Container Runtimes 비교 표](https://great-stone.github.io/container/ContainerRuntimesSheet/)
448 | - [Custom Metric(ex. RPS)으로 HPA 설정하기](https://tech.scatterlab.co.kr/kubernetes-hpa-custom-metric/)
449 | - [etcd란?](https://www.redhat.com/ko/topics/containers/what-is-etcd)
450 | - [For the love of god, stop using CPU limits on Kubernetes (updated)](https://home.robusta.dev/blog/stop-using-cpu-limits)
451 | - [HA(High Availability) 구성 - master node](https://psnote.tistory.com/210)
452 | - [Hello Minikube](https://kubernetes.io/ko/docs/tutorials/hello-minikube/)
453 | - [Helm 이란?](https://tech.ktcloud.com/51)
454 | - [HPA: Horizontal Pod Autoscaling](https://kubernetes.io/ko/docs/tasks/run-application/horizontal-pod-autoscale/)
455 | - [How To Manage Your Kubernetes Configurations with Kustomize](https://www.digitalocean.com/community/tutorials/how-to-manage-your-kubernetes-configurations-with-kustomize)
456 | - [Istio Sidecar Injection](http://itnp.kr/post/istio-injection-automatically-installing-sidecar-on-the-pod-in-use)
457 | - [Istio 🌶️트래픽 흐름 Life of a packet](https://www.notion.so/Istio-Life-of-a-packet-6ad9808e14594296bf854dcc203cab71)
458 | - [Istio란 무엇인가?](https://twofootdog.tistory.com/78)
459 | - [Istio 아키텍처와 기능 이해하기](https://velog.io/@beryl/Istio-%EA%B0%9C%EB%85%90)
460 | - [Job/CronJob](https://kimjingo.tistory.com/135)
461 | - [[K8S] Control Plane, Data Plane이란?](https://wooono.tistory.com/700)
462 | - [k8s fission](https://fission.io/)
463 | - [k8s kind](https://kind.sigs.k8s.io/)
464 | - [k8s 인증 완벽이해 #1 - X.509 Client Certs](https://coffeewhale.com/kubernetes/authentication/x509/2020/05/02/auth01/)
465 | - [[k8s] 쿠버네티스 애플리케이션 접근 구성하기: NodePort, Ingress, Istio](https://wrynn.tistory.com/66)
466 | - [Kubernetes Calico Plugin](https://ssup2.github.io/theory_analysis/Kubernetes_Calico_Plugin/)
467 | - [kubernetes Pod의 진단을 담당하는 서비스 : probe](https://medium.com/finda-tech/kubernetes-pod%EC%9D%98-%EC%A7%84%EB%8B%A8%EC%9D%84-%EB%8B%B4%EB%8B%B9%ED%95%98%EB%8A%94-%EC%84%9C%EB%B9%84%EC%8A%A4-probe-7872cec9e568)
468 | - [Kubernetes 운영을 위한 etcd 기본 동작 원리의 이해](https://tech.kakao.com/2021/12/20/kubernetes-etcd/)
469 | - [[kubernetes] 쿠버네티스 cr과 crd란?(쿠버네티스 확장)]()
470 | - [Kubernetes의 HPA를 활용한 오토스케일링(Auto Scaling)](https://medium.com/dtevangelist/k8s-kubernetes%EC%9D%98-hpa%EB%A5%BC-%ED%99%9C%EC%9A%A9%ED%95%9C-%EC%98%A4%ED%86%A0%EC%8A%A4%EC%BC%80%EC%9D%BC%EB%A7%81-auto-scaling-2fc6aca61c26)
471 | - [Kubernetes Istio 설치/적용하기 (Kubernetes Istio service mesh)](https://joobly.tistory.com/60)
472 | - [kubectl 개요](https://kubernetes.io/ko/docs/reference/kubectl/overview/)
473 | - [Kubernetes : Local에 설치하기](https://velog.io/@sixhustle/k8s-started-1)
474 | - [Kubernetes 좀 더 잘 이해하기](https://suhwan.dev/2019/04/22/understanding-kubernetes-design/)
475 | - [Kubernetes 환경에 affinity, anti-affinity 적용하기](https://malgogi-developer.tistory.com/32)
476 | - [Pod 스케쥴링 #2 Affinity](https://bcho.tistory.com/1346)
477 | - [Rancher](https://www.rancher.com/)
478 | - [Understanding Envoy Rate Limits](https://www.aboutwayfair.com/tech-innovation/understanding-envoy-rate-limits)
479 | - [공인 쿠버네티스 자격증 알아보기 (CKA, CKAD, CKS, KCNA)](https://hong-sam.tistory.com/179)
480 | - [라즈베리 파이로 쿠버네티스 클러스터를 만들어보자.](https://www.binaryflavor.com/raspberry-pi-kubernetes-1/)
481 | - [쓰기만 했던 개발자가 궁금해서 찾아본 쿠버네티스 내부](https://tech.kakaopay.com/post/jack-k8s-internals-part-1/)
482 | - [워크로드 리소스](https://kubernetes.io/ko/docs/concepts/workloads/controllers/)
483 | - [커스텀 리소스](https://kubernetes.io/ko/docs/concepts/extend-kubernetes/api-extension/custom-resources/)
484 | - [커스텀 측정항목을 통한 쿠버네티스 오토스케일링(custom metrics kuberntes autoscaling) - presto(1/2) - 사전작업](https://cce199.tistory.com/62)
485 | - [쿠버네티스 #9 - HealthCheck](https://bcho.tistory.com/1264)
486 | - [쿠버네티스 교육과 인증(공식)](https://kubernetes.io/ko/training/)
487 | - [쿠버네티스 프로비저닝 툴과의 만남부터 헤어짐까지 . . .](https://tech.kakao.com/2023/02/10/making-of-kubernetes-provisioning-tool/)
488 | - [쿠버네티스 문서(공식)](https://kubernetes.io/ko/docs/home/)
489 | - [쿠버네티스 컴포넌트](https://kubernetes.io/ko/docs/concepts/overview/components/)
490 | - [쿠버네티스 cordon, drain](https://arisu1000.tistory.com/27845)
491 | - [쿠버네티스 Ingress 개념 및 적용방법](https://twofootdog.tistory.com/23)
492 | - [쿠버네티스 - 매니페스트, YAML파일, 파드(manifest, YAML 파일, pod)](https://blog.naver.com/PostView.naver?blogId=ghdalswl77&logNo=222388293445&parentCategoryNo=&categoryNo=90&viewDate=&isShowPopularPosts=true&from=search)
493 | - [파드 라이프사이클](https://kubernetes.io/ko/docs/concepts/workloads/pods/pod-lifecycle/)
494 | - [프라이빗 레지스트리에서 이미지 받아오기](https://kubernetes.io/ko/docs/tasks/configure-pod-container/pull-image-private-registry/)
495 | - Prometheus
496 | - [MySQL 데이터 모니터링 – Prometheus MySQL Expoter](http://mysqldbadmtech.blogspot.com/2016/12/pmm-180-mysql-prometheus-mysql-exporter.html)
497 | - [Prometheus란?](https://medium.com/finda-tech/prometheus%EB%9E%80-cf52c9a8785f)
498 | - [Prometheus란 무엇인가](https://gurumee92.tistory.com/220)
499 | - [Prometheus and Grafana setup in Minikube](https://blog.marcnuri.com/prometheus-grafana-setup-minikube)
500 |
501 | ## 알고리즘
502 |
503 | - [DFS와 BFS](https://this-programmer.tistory.com/entry/%EB%B0%B1%EC%A4%801260%ED%8C%8C%EC%9D%B4%EC%8D%AC-DFS%EC%99%80-BFS)
504 | - [FizzBuzz 문제](https://bryan.wiki/260)
505 | - [Levenshtein Distance (편집거리 알고리즘) - 문장 유사도 분석을 어떻게 하는가?](https://renuevo.github.io/data-science/levenshtein-distance/)
506 | - [Lock Free 알고리즘(Non-Blocking 알고리즘)](https://effectivesquid.tistory.com/entry/Lock-Free-%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98Non-Blocking-%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98)
507 | - [Lucene ANN 분석1 - HNSW algorithm](https://chocolate-life.tistory.com/11)
508 | - [RAFT ALGORITHM](https://dinonotes.com/archives/909#:~:text=RAFT%20%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98%EC%9D%80%20Consensus%20Algorithm,%ED%95%A9%EC%9D%98%EB%A5%BC%20%ED%95%98%EB%8A%94%20%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98%EC%9D%B4%EB%8B%A4.)
509 | - [논 블로킹 알고리즘(Non-blocking Algorithms)](https://parkcheolu.tistory.com/33)
510 | - [대충? 거의 정확하다! 벡터 검색 엔진에 ANN HNSW 알고리즘 도입기 (feat. SWIG Golang)](https://forward.nhn.com/2022/sessions/42)
511 | - [동적 계획법(Dynamic Programming)](https://ko.wikipedia.org/wiki/%EB%8F%99%EC%A0%81_%EA%B3%84%ED%9A%8D%EB%B2%95)
512 | - [레벤슈타인 거리를 이용해서 두 문장 비교하기](https://hoony-gunputer.tistory.com/entry/%EB%A0%88%EB%B2%A4%EC%8A%88%ED%83%80%EC%9D%B8-%EA%B1%B0%EB%A6%AC%EB%A5%BC-%EC%9D%B4%EC%9A%A9%ED%95%B4%EC%84%9C-%EB%91%90-%EB%AC%B8%EC%9E%A5-%EB%B9%84%EA%B5%90%ED%95%98%EA%B8%B0#:~:text=%EB%A0%88%EB%B2%A4%EC%8A%88%ED%83%80%EC%9D%B8%20%EA%B1%B0%EB%A6%AC%EB%8A%94%20%EB%8F%85%EC%9D%BC%EC%9D%98,%EB%8B%A4%EB%A5%B8%EC%A7%80%20%EA%B5%AC%EB%B6%84%ED%95%98%EB%8A%94%20%EB%B0%A9%EB%B2%95%EC%9D%B4%EB%8B%A4.)
513 | - [벡터 검색은 무엇인가요?](https://www.elastic.co/kr/what-is/vector-search)
514 | - [벡터 유사도 검색이 무엇인가요? (What is Vector Similarity Search?)](https://devocean.sk.com/blog/techBoardDetail.do?ID=165293)
515 | - [브루트 포스(Brute Force)](https://steemit.com/kr-dev/@gyeryak/easyalgo-2-bruteforce)
516 | - [빅오 표기법(Big-O Notation), 시간 복잡도, 공간 복잡도](https://cjh5414.github.io/big-o-notation/)
517 | - [에라토스테네스의 체(Sieve of Eratosthenes)](https://ko.wikipedia.org/wiki/%EC%97%90%EB%9D%BC%ED%86%A0%EC%8A%A4%ED%85%8C%EB%84%A4%EC%8A%A4%EC%9D%98_%EC%B2%B4)
518 | - [이진탐색](https://namu.wiki/w/%EC%9D%B4%EC%A7%84%20%ED%83%90%EC%83%89)
519 | - [정렬 알고리즘](https://namu.wiki/w/%EC%A0%95%EB%A0%AC%20%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98)
520 | - [정렬 알고리즘 비교](https://ratsgo.github.io/data%20structure&algorithm/2017/10/19/sort/)
521 | - [탐욕법(Greedy Algorithm)과 그 종류](https://janghw.tistory.com/entry/%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98-Greedy-Algorithm-%ED%83%90%EC%9A%95-%EC%95%8C%EA%B3%A0%EB%A6%AC%EC%A6%98)
522 | - [퍼지 문자열 검색(Fuzzy string search)](https://juggernaut.tistory.com/entry/%ED%8D%BC%EC%A7%80-%EB%AC%B8%EC%9E%90%EC%97%B4-%EA%B2%80%EC%83%89Fuzzy-string-search)
523 | - [피보나치 수열을 구하는 세 가지 방법. (재귀, 동적 계획법, 반복)](https://makefortune2.tistory.com/60)
524 | - [해시 함수](https://ko.wikipedia.org/wiki/%ED%95%B4%EC%8B%9C_%ED%95%A8%EC%88%98)
525 |
526 | ## 연구논문
527 |
528 | - [Attention is All you Need](https://papers.nips.cc/paper/2017/hash/3f5ee243547dee91fbd053c1c4a845aa-Abstract.html)
529 |
530 | ## 자료구조
531 |
532 | - [B-Tree, B+ Tree(Gone)](https://ssup2.github.io/theory_analysis/B_Tree_B+_Tree/)
533 | - [B-트리(B-Tree)란? B트리 탐색, 삽입, 삭제 과정](https://velog.io/@chanyoung1998/B%ED%8A%B8%EB%A6%AC)
534 | - [Data Structure Visualizations](https://www.cs.usfca.edu/~galles/visualization/Algorithms.html)
535 | - [Hash, Hashing, Hash Table(해시, 해싱 해시테이블) 자료구조의 이해](https://velog.io/@cyranocoding/Hash-Hashing-Hash-Table%ED%95%B4%EC%8B%9C-%ED%95%B4%EC%8B%B1-%ED%95%B4%EC%8B%9C%ED%85%8C%EC%9D%B4%EB%B8%94-%EC%9E%90%EB%A3%8C%EA%B5%AC%EC%A1%B0%EC%9D%98-%EC%9D%B4%ED%95%B4-6ijyonph6o)
536 | - [Linked list (연결 리스트) 란 무엇인가?](https://supermemi.tistory.com/67)
537 | - [Rope](https://en.wikipedia.org/wiki/Rope_(data_structure))
538 | - [Star (graph theory)](https://en.wikipedia.org/wiki/Star_(graph_theory))
539 | - [Speed up millions of regex replacements in Python 3](https://stackoverflow.com/questions/42742810/speed-up-millions-of-regex-replacements-in-python-3)
540 | - [YAML](https://ko.wikipedia.org/wiki/YAML)
541 | - [YAML이란?](https://www.redhat.com/ko/topics/automation/what-is-yaml)
542 | - [[자료구조] 간단히 알아보는 B-Tree, B+Tree, B*Tree](https://ssocoit.tistory.com/217)
543 | - [그래프 이론 기초 & 그래프 패턴](https://blahblahlab.tistory.com/140)
544 | - [배열(Array)과 리스트(List)](https://wayhome25.github.io/cs/2017/04/17/cs-18-1/)
545 | - [이진 트리(Binary Tree)의 종류](https://hsc-tech.tistory.com/7)
546 | - [이진 트리](https://thebook.io/007031/part01/ch03/07/01/)
547 | - [이진탐색트리(Binary Search Tree)](https://ratsgo.github.io/data%20structure&algorithm/2017/10/22/bst/)
548 | - [자료구조와 시간복잡도](https://daelumgi.postype.com/post/5270208)
549 | - [퍼지 문자열 검색(Fuzzy string search)](https://juggernaut.tistory.com/entry/%ED%8D%BC%EC%A7%80-%EB%AC%B8%EC%9E%90%EC%97%B4-%EA%B2%80%EC%83%89Fuzzy-string-search)
550 | - [해시맵 (HashMap) / 맵 (Map)](https://hapbbying.tistory.com/81)
551 | - [효율적인 긴 문자열 연산을 위한 Rope 자료구조](http://www.secmem.org/blog/2019/03/09/rope/)
552 | - [힙(heap)이란](https://gmlwjd9405.github.io/2018/05/10/data-structure-heap.html)
553 |
554 | ## 언어와 프레임워크
555 |
556 | - CSS
557 | - [FLEXBOX FROGGY](https://flexboxfroggy.com/#ko)
558 | - [GRID GARDEN](https://cssgridgarden.com/#ko)
559 | - 고(go)
560 | - [Defer, Panic, and Recover](https://go.dev/blog/defer-panic-and-recover)
561 | - [Golang 에서의 명명 규칙](https://blog.billo.io/devposts/golang_naming_convention/)
562 | - [Go YAML](https://zetcode.com/golang/yaml/)
563 | - [Go CLI - Go Developer Road Map](https://earntrust.tistory.com/entry/gdrm-go-cli)
564 | - [Go: flag 패키지로 CLI 도구 만들기](https://pronist.dev/97)
565 | - [Go언어로 나만의 Query Exporter 만들어보기!](https://gywn.net/2021/07/make-own-query-exporter-with-go/)
566 | - [How to create a CLI in golang with cobra](https://towardsdatascience.com/how-to-create-a-cli-in-golang-with-cobra-d729641c7177)
567 | - [표준 Go 프로젝트 레이아웃(Standard Go Project Layout)](https://byounghoonkim.github.io/posts/2020-06-27-go-project-layout/)
568 | - 러스트(Rust)
569 | - [Rust by Example](https://doc.rust-lang.org/rust-by-example/index.html)
570 | - [The Rust Programming Language(en)](https://doc.rust-lang.org/book/title-page.html)
571 | - [The Rust Programming Language(ko)](https://rinthel.github.io/rust-lang-book-ko/foreword.html)
572 | - [일주일만에 Rust에 매료되다](https://blog.appleseed.dev/post/fascinated-by-rust-in-a-week/)
573 | - [파이썬 프로그래머를 위한 러스트 입문](https://indosaram.github.io/rust-python-book/)
574 | - 쉘 스크립트(shell script)
575 | - [Bash 실행결과를 변수에 담기](https://zetawiki.com/wiki/Bash_%EC%8B%A4%ED%96%89%EA%B2%B0%EA%B3%BC%EB%A5%BC_%EB%B3%80%EC%88%98%EC%97%90_%EB%8B%B4%EA%B8%B0)
576 | - 엘릭서(Elixir)
577 | - [Elixir(엘릭서) 동시성 프로그래밍 - 1. 경량 프로세스](https://velog.io/@gudrb33333/Elixir%EC%97%98%EB%A6%AD%EC%84%9C-%EB%8F%99%EC%8B%9C%EC%84%B1-%ED%94%84%EB%A1%9C%EA%B7%B8%EB%9E%98%EB%B0%8D-1.-%EA%B2%BD%EB%9F%89-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4)
578 | - 자바(Java)
579 | - [코드로 알아보는 java의 Hashmap](https://sabarada.tistory.com/57)
580 | - 자바스크립트(Javascript)
581 | - [[JavaScript] - 커링에 대해 알아보자]()
582 | - [var, let, const 차이점](https://velog.io/@bathingape/JavaScript-var-let-const-%EC%B0%A8%EC%9D%B4%EC%A0%90)
583 | - [자바스크립트의 변수범위와 호이스팅](http://chanlee.github.io/2013/12/10/javascript-variable-scope-and-hoisting/)
584 | - Node.js
585 | - [로우 레벨로 살펴보는 Node.js 이벤트 루프](https://evan-moon.github.io/2019/08/01/nodejs-event-loop-workflow/)
586 | - Svelte
587 | - [How to deploy svelte app in Github Pages](https://hrishikeshpathak.com/blog/svelte-gh-pages/)
588 | - [SvelteKit Introduction](https://kit.svelte.dev/docs/introduction)
589 | - 타입스크립트(TypeScript)
590 | - [타입스크립트 모노레포](https://deptno.github.io/posts/2018/typescript-monorepo/)
591 | - 파이썬(Python)
592 | - [A guide to logging in Python](https://www.bloomberg.com/company/stories/guide-logging-python/)
593 | - [containerd를 런타임으로 사용한 Kubernetes 설치](https://docmoa.github.io/02-Private%20Platform/Kubernetes/02-Config/kubernetes_with_out_docker.html)
594 | - [[CS/Python]Thread(1)-GIL과 Thread 구현/실행, Event](https://velog.io/@jaewan/CSPythonThread1)
595 | - [[CS/Python]Thread(2)-Lock과 RLock](https://velog.io/@jaewan/CSPythonThread2)
596 | - [[CS/Python]Thread(3)-Condition, Lock, Mutex, Semaphore, Local Data](https://velog.io/@jaewan/CSPythonThread3-Condition-Lock-Mutex-Semaphore-Local-Data)
597 | - [Dependency injection and inversion of control in Python](https://python-dependency-injector.ets-labs.org/introduction/di_in_python.html)
598 | - [Garbage Collection in Python](https://medium.com/dmsfordsm/garbage-collection-in-python-777916fd3189)
599 | - [How Python Asyncio Works: Recreating it from Scratch](https://jacobpadilla.com/articles/recreating-asyncio)
600 | - [How to Flatten a Dictionary in Python in 4 Different Ways](https://www.freecodecamp.org/news/how-to-flatten-a-dictionary-in-python-in-4-different-ways/)
601 | - [How to set up HTTPHandler for python logging](https://stackoverflow.com/questions/51525237/how-to-set-up-httphandler-for-python-logging)
602 | - [Instagram이 Python garbage collection 없앤 이유](https://luavis.me/python/dismissing-python-garbage-collection-at-instagram)
603 | - [PEP 20 – The Zen of Python](https://peps.python.org/pep-0020/)
604 | - [[pytest] python 코드를 테스트 해봅시다. (Feat. Fixture)]()
605 | - [Python 개발자를 위한 gevent](http://leekchan.com/gevent-tutorial-ko/)
606 | - [python functools.partial 사용](https://tempdev.tistory.com/36)
607 | - [[Python] GIL (Global Interpreter Lock) 이해하기](https://it-eldorado.tistory.com/160)
608 | - [[Python] Interpreter and PVM (Python Virtual Machine)](https://dsaint31.tistory.com/entry/Python-Interpreter-and-PVM-Python-Virtual-Machine)
609 | - [[python] Iterator와 Generator](https://engineer-mole.tistory.com/64)
610 | - [Python logging json formatter](https://everythingtech.dev/2021/03/python-logging-with-json-formatter/)
611 | - [[Python] metaclass란](https://brownbears.tistory.com/569)
612 | - [Python multiprocessing's Pool process limit](https://stackoverflow.com/questions/20039659/python-multiprocessings-pool-process-limit)
613 | - [Python multiprocessing.Process 멀티프로세싱 1](https://tempdev.tistory.com/26)
614 | - [Python multiprocessing.Pool 멀티프로세싱 2](https://tempdev.tistory.com/27)
615 | - [python pool.map() and shared array variable](https://stackoverflow.com/questions/56585130/python-pool-map-and-shared-array-variable)
616 | - [python 동시성 관리 (1) - 프로세스(Process)와 스레드(Thread)](https://velog.io/@jaebig/python-%EB%8F%99%EC%8B%9C%EC%84%B1-%EA%B4%80%EB%A6%AC-1-%ED%94%84%EB%A1%9C%EC%84%B8%EC%8A%A4Process%EC%99%80-%EC%8A%A4%EB%A0%88%EB%93%9CThread)
617 | - [python 동시성 관리 (2) - GIL(Global Interpreter Lock)](https://velog.io/@jaebig/python-%EB%8F%99%EC%8B%9C%EC%84%B1-%EA%B4%80%EB%A6%AC-2-GILGlobal-Interpreter-Lock)
618 | - [python 동시성 관리 (3) - 코루틴(Coroutine)이란?](https://velog.io/@jaebig/python-%EB%8F%99%EC%8B%9C%EC%84%B1-%EA%B4%80%EB%A6%AC-3-%EC%BD%94%EB%A3%A8%ED%8B%B4Coroutine)
619 | - [[Python] 클래스의 인스턴스 변수 protected, private(접근 제어자)](https://minimin2.tistory.com/182)
620 | - [[python] 파이썬 is와 ==의 차이 (값, 참조)](https://blockdmask.tistory.com/579)
621 | - [Pytorch weight 저장에 대해 우리가 알아야하는 모든 것](https://comlini8-8.tistory.com/50)
622 | - [Rusty Python](https://rangho.postype.com/post/6680526)
623 | - [Speed up millions of regex replacements in Python 3](https://stackoverflow.com/questions/42742810/speed-up-millions-of-regex-replacements-in-python-3)
624 | - [SQLAlchemy의 연결 풀링 이해하기](https://spoqa.github.io/2018/01/17/connection-pool-of-sqlalchemy.html)
625 | - [staticmethod, classmethod, instancemethod 에 대하여](https://hwan-hobby.tistory.com/252)
626 | - [Tool for generating SQLAlchemy queries from JSON-esque values?](https://stackoverflow.com/questions/10342700/tool-for-generating-sqlalchemy-queries-from-json-esque-values)
627 | - [Understand 5 Scopes of Pytest Fixtures](https://betterprogramming.pub/understand-5-scopes-of-pytest-fixtures-1b607b5c19ed)
628 | - [고성능 ML 백엔드를 위한 10가지 Python 성능 최적화 팁](https://hyperconnect.github.io/2023/05/30/Python-Performance-Tips.html?fbclid=IwAR2jFLVANvYblyCYoVVFZKST-pe7JqGtSduoaoMnBZunlR2EHm3mz0ySRHc&mibextid=DcJ9fc)
629 | - [데코레이터(decorator)란?](https://hello-bryan.tistory.com/214)
630 | - [제네레이터(generator)란?(1)](https://bluese05.tistory.com/56)
631 | - [제네레이터(generator)란?(2)](https://wikidocs.net/16069)
632 | - [조금 더 체계적인 Python Logging](https://hwangheek.github.io/2019/python-logging/)
633 | - [튜플(tuple), 리스트(list), 셋(set), 딕셔너리(dict) 비교](https://specialscene.tistory.com/142#:~:text=%EB%A6%AC%EC%8A%A4%ED%8A%B8%EC%99%80%20%EB%B9%84%EA%B5%90%EA%B0%80%20%EB%A7%8E%EC%9D%B4,%ED%95%98%EA%B1%B0%EB%82%98%20%EB%B3%80%EA%B2%BD%ED%95%A0%20%EC%88%98%20%EC%97%86%EB%8B%A4%EB%8A%94%20%EA%B2%83.)
634 | - [파이썬 세 개의 점, ELLIPSIS 객체는 무엇인가요?](https://tech.madup.com/python-ellipsis/)
635 | - [파이썬 Object Interning](http://pythonstudy.xyz/python/article/512-%ED%8C%8C%EC%9D%B4%EC%8D%AC-Object-Interning)
636 | - [파이썬의 global과 nonlocal 키워드 사용법](https://www.daleseo.com/python-global-nonlocal/)
637 | - [파이썬의 대표적인 네 자료형(리스트, 셋, 튜플, 딕셔너리) 특성 알아보기](https://this-programmer.tistory.com/445)
638 | - [파이썬의 유닛테스트를 한번에 파악할 수 있는 코드](https://this-programmer.tistory.com/502)
639 | - [파이썬 의존성 관리자 Poetry 사용기](https://spoqa.github.io/2019/08/09/brand-new-python-dependency-manager-poetry.html)
640 | - [파이썬 인터닝 (Python Interning) - 객체 재사용](https://this-programmer.tistory.com/508)
641 | - [파이썬 프로그래머를 위한 러스트 입문](https://indosaram.github.io/rust-python-book/)
642 | - [파이썬 함수의 매개변수에 쓰이는 bare asterisk(*)의 의미](https://this-programmer.tistory.com/503)
643 | - AsyncIO
644 | - [asyncio 파헤치기](https://brownbears.tistory.com/540)
645 | - [asyncio 뽀개기 1 - Coroutine과 Eventloop](https://tech.buzzvil.com/blog/asyncio-no-1-coroutine-and-eventloop/)
646 | - [asyncio 뽀개기 2 - Future의 활용](https://tech.buzzvil.com/blog/asyncio-no-2-future/)
647 | - [asyncio 뽀개기 3 - SIGTERM (CTRL+C) 올바르게 처리하기](https://tech.buzzvil.com/blog/asyncio-no-3-sigterm/)
648 | - [파이썬과 비동기 프로그래밍 #1, 비동기 프로그래밍이란](https://sjquant.tistory.com/13)
649 | - 장고(Django)
650 | - [APIView, Mixins, generics APIView, ViewSet을 알아보자](https://ssungkang.tistory.com/entry/Django-APIView-Mixins-generics-APIView-ViewSet%EC%9D%84-%EC%95%8C%EC%95%84%EB%B3%B4%EC%9E%90?category=366160)
651 | - [ViewSet 과 Router](https://ssungkang.tistory.com/entry/Django-ViewSet-%EA%B3%BC-Router)
652 | - FastAPI
653 | - [Dependency Injector를 이용한 의존성 관리](https://blog.neonkid.xyz/279?category=434025#)
654 | - [Dependency Injector + FastAPI + SQLAlchemy example](https://python-dependency-injector.ets-labs.org/examples/fastapi-sqlalchemy.html)
655 | - [FastAPI Schema를 제대로 다루는 방법](https://this-programmer.tistory.com/471)
656 | - [FastAPI + SQLAlchemy example](https://python-dependency-injector.ets-labs.org/examples/fastapi-sqlalchemy.html)
657 |
658 | ## 운영체제
659 |
660 | - [Deadlock 개념이란? 그에 대한 해결책/회피책](https://jwprogramming.tistory.com/12)
661 | - [Swap memory](https://monny.tistory.com/253#:~:text=Swapping%EC%9D%80%20%EC%BB%B4%ED%93%A8%ED%84%B0%20%EC%8B%A4%EC%A0%9C%20%EB%A9%94%EB%AA%A8%EB%A6%AC,%EA%B3%BC%20RAM%EC%9D%98%20%EC%A1%B0%ED%95%A9%EC%9E%85%EB%8B%88%EB%8B%A4.)
662 | - [데드락(Deadlock, 교착 상태)이란?](https://chanhuiseok.github.io/posts/cs-2/)
663 | - [운영 체제(위키)](https://ko.wikipedia.org/wiki/%EC%9A%B4%EC%98%81_%EC%B2%B4%EC%A0%9C)
664 | - 리눅스(Linux) / 유닉스(Unix)
665 | - [cgroup 이란?](https://sonseungha.tistory.com/535)
666 | - [exit code](https://velog.io/@legendre13/exit-code)
667 | - [Linux - Namespace 란?](https://galid1.tistory.com/442)
668 | - [NFS서버란 무엇인가?](https://jhnyang.tistory.com/279)
669 | - [supervisor를 사용하여 지속적으로 실행해야 하는 프로세스 관리하기](https://m.blog.naver.com/PostView.naver?isHttpsRedirect=true&blogId=shino1025&logNo=221472860840)
670 | - [Ubuntu iptables 저장, 리부팅 뒤 자동 복구](https://salsalchanchan.tistory.com/14)
671 | - [리눅스(Linux)와 유닉스(Unix)의 차이](https://this-programmer.tistory.com/entry/%EB%A6%AC%EB%88%85%EC%8A%A4Linux%EC%99%80-%EC%9C%A0%EB%8B%89%EC%8A%A4Unix%EC%9D%98-%EC%B0%A8%EC%9D%B4)
672 | - [리눅스 네임스페이스(Linux Namespace)란?](https://www.44bits.io/ko/keyword/linux-namespace)
673 | - [리눅스 리다이렉션 & 파이프(Linux redirection & pipe)](https://jdm.kr/blog/74)
674 | - [리눅스, 유닉스 백그라운드프로세스 방법 정리 (&, bg, nohup, screen)](https://this-programmer.tistory.com/468)
675 |
676 | ## 인공지능
677 |
678 | - [Classification & Clustering 모델 평가](https://bcho.tistory.com/1206)
679 | - [Embedding이란 무엇이고, 어떻게 사용하는가?](https://www.syncly.app/ko/blog/what-is-embedding-and-how-to-use)
680 | - [Extracting Features from an Intermediate Layer of a Pretrained VGG-Net in PyTorch](https://medium.com/the-owl/extracting-features-from-an-intermediate-layer-of-a-pretrained-vgg-net-in-pytorch-43f801866a2e)
681 | - [Mapping the Mind of a Large Language Model](https://www.anthropic.com/research/mapping-mind-language-model)
682 | - [MLOps 란 무엇일까?](https://medium.com/daria-blog/mlops-%EB%9E%80-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C-7ba8d9aae221)
683 | - [MLOps란? MLOps가 꼭 필요한 이유](https://elice.io/ko/newsroom/whats_mlops)
684 | - [nvidia-docker GPU 할당하여 사용 하는 방법 3가지](https://iamreo.tistory.com/entry/nvidia-docker-GPU-%ED%95%A0%EB%8B%B9%ED%95%98%EC%97%AC-%EC%82%AC%EC%9A%A9-%ED%95%98%EB%8A%94-%EB%B0%A9%EB%B2%95-3%EA%B0%80%EC%A7%80)
685 | - [Scaling Monosemanticity: Extracting Interpretable Features from Claude 3 Sonnet](https://transformer-circuits.pub/2024/scaling-monosemanticity/index.html)
686 | - [Study Artificial Intelligence](http://www.aistudy.co.kr/)
687 | - [The two-pizza rule and the secret of Amazon's success](https://www.theguardian.com/technology/2018/apr/24/the-two-pizza-rule-and-the-secret-of-amazons-success)
688 | - [The Ultimate Guide to Deep Learning Model Quantization and Quantization-Aware Training](https://deci.ai/quantization-and-quantization-aware-training/)
689 | - [Using LLaMA with M1 Mac](https://dev.l1x.be/posts/2023/03/12/using-llama-with-m1-mac/)
690 | - [llama : Metal inference](https://github.com/ggerganov/llama.cpp/pull/1642?fbclid=IwAR0JMfY-AxX5_stcGLvJn7u_XoP0uTR0OuI9vGzyd4crXBKWiToJbZ7Hgs8)
691 | - [규칙 기반 학습 (Rule Based Learning)](https://yngie-c.github.io/machine%20learning/2020/04/05/rule_based/)
692 | - [딥러닝이란 무엇인가](https://tensorflow.blog/%EC%BC%80%EB%9D%BC%EC%8A%A4-%EB%94%A5%EB%9F%AC%EB%8B%9D/1-%EB%94%A5%EB%9F%AC%EB%8B%9D%EC%9D%B4%EB%9E%80-%EB%AC%B4%EC%97%87%EC%9D%B8%EA%B0%80/)
693 | - [머신러닝 분야의 임베딩에 대한 상세한 가이드 (The Full Guide to Embeddings in Machine Learning)](https://discuss.pytorch.kr/t/the-full-guide-to-embeddings-in-machine-learning/1708)
694 | - [아마존 제프 베조스의 '피자 두 판의 법칙'](https://www.ttimes.co.kr/article/2015102814057788682)
695 | - [언어모델의 원리와 만들기](https://tech.kakao.com/2023/06/05/languagemodel-mlm-clm/)
696 | - [인공지능에서 양자화 기술이 중요한 이유는?](https://m.post.naver.com/viewer/postView.nhn?volumeNo=19437431&memberNo=20717909)
697 | - [저전력 인공지능(AI) 구현을 가능케 하는 알고리즘은?](https://m.post.naver.com/viewer/postView.nhn?volumeNo=16696626&memberNo=20717909)
698 | - [[추천시스템] Cold Start 문제는 어떻게 해결할까?]()
699 | - [파이토치 한국 사용자 모임](https://pytorch.kr/)
700 |
701 | ## 좋은 글들
702 |
703 | - [APM (Application Performance management)](https://blog.daum.net/ossogood/8435674)
704 | - [awesome-devteam](https://github.com/leehosung/awesome-devteam)
705 | - [CRM이란 무엇인가요?](https://www.oracle.com/kr/cx/what-is-crm/)
706 | - [Git 커밋 메시지는 왜 중요할까?](https://insight.infograb.net/blog/2023/04/21/why-commit-convention-is-important/)
707 | - [Improving Distributed Caching Performance and Efficiency at Pinterest](https://medium.com/pinterest-engineering/improving-distributed-caching-performance-and-efficiency-at-pinterest-92484b5fe39b)
708 | - [Inventing on Principle](https://lilys.ai/digest/211430)
709 | - [IT직군에서 많이 쓰이는 SI, SM, SE, PG 등 용어의 의미](https://this-programmer.tistory.com/entry/IT%EC%A7%81%EA%B5%B0%EC%97%90%EC%84%9C-%EB%A7%8E%EC%9D%B4-%EC%93%B0%EC%9D%B4%EB%8A%94-SI-SM-SE-PG-%EB%93%B1-%EC%9A%A9%EC%96%B4%EC%9D%98-%EC%9D%98%EB%AF%B8)
710 | - [Machines of Loving Grace](https://darioamodei.com/machines-of-loving-grace)
711 | - [OKR이란?](https://experience.dropbox.com/ko-kr/resources/what-is-an-okr)
712 | - [POC (Proof Of Concept)란?](https://m.blog.naver.com/pmw9440/221763425946)
713 | - [StackExchangePerformance](https://stackexchange.com/performance)
714 | - [StackOverflow는 9대의 on-prem 서버로 운영중](https://news.hada.io/topic?id=6993&utm_source=slack&utm_medium=bot&utm_campaign=T02VBL70FGV)
715 | - [Y Combinator 인터뷰 + 탈락 썰](https://ssowonny.medium.com/y-combinator-%EC%9D%B8%ED%84%B0%EB%B7%B0-%ED%83%88%EB%9D%BD-%EC%8D%B0-cb8a8a00ef03)
716 | - [가장 효과적인 창업자들을 연구해서 얻은 교훈들](https://news.hada.io/topic?id=6792&utm_source=slack&utm_medium=bot&utm_campaign=T02VBL70FGV)
717 | - [국내 최고의 개발 문화를 가진 회사는? - 설문 조사 결과](http://channy.creation.net/blog/1600)
718 | - [네이버 메인 페이지의 트래픽 처리](https://d2.naver.com/helloworld/6070967)
719 | - [소프트웨어, 실무형 인재의 신화](https://sangminpark.blog/2011/08/26/%EC%86%8C%ED%94%84%ED%8A%B8%EC%9B%A8%EC%96%B4-%EC%8B%A4%EB%AC%B4%ED%98%95-%EC%9D%B8%EC%9E%AC%EC%9D%98-%EC%8B%A0%ED%99%94/)
720 | - [아마존(Amazon)에서 배운 5가지 글쓰기와 소통 방식](http://channy.creation.net/blog/1620)
721 | - [애자일 소프트웨어 개발 선언](https://agilemanifesto.org/iso/ko/manifesto.html)
722 | - [웹 브라우저에 URL을 입력하면 어떤 일이 생기나요?](https://aws.amazon.com/ko/blogs/korea/what-happens-when-you-type-a-url-into-your-browser/)
723 | - [주니어, 미드레벨과 시니어 개발자의 차이점](https://erwinousy.medium.com/%EC%A3%BC%EB%8B%88%EC%96%B4-%EB%AF%B8%EB%93%9C%EB%A0%88%EB%B2%A8%EA%B3%BC-%EC%8B%9C%EB%8B%88%EC%96%B4-%EA%B0%9C%EB%B0%9C%EC%9E%90%EC%9D%98-%EC%B0%A8%EC%9D%B4%EC%A0%90-d29bffecfec#:~:text=%EC%8B%9C%EB%8B%88%EC%96%B4%20%EA%B0%9C%EB%B0%9C%EC%9E%90%EB%8A%94%20%EC%A3%BC%EB%8B%88%EC%96%B4%20%EA%B0%9C%EB%B0%9C,%EC%9E%91%EB%8F%99%EC%8B%9C%ED%82%AC%20%EC%83%9D%EA%B0%81%EB%A7%8C%20%ED%95%A9%EB%8B%88%EB%8B%A4.)
724 | - [컴퓨팅 사고와 개발 실력 늘리는 공부법](https://velog.io/@teo/computational-thinking)
725 | - [통합관제 EMS(종합관제)](http://hamonsoft.co.kr/solution/integrated-control/integrated-management/netis-ems/)
726 |
727 | ## 컴퓨터 공학
728 |
729 | - [[CISC / RISC] 개념 및 차이](https://velog.io/@kjw2298/CISC-RISC-%EA%B0%9C%EB%85%90-%EB%B0%8F-%EC%B0%A8%EC%9D%B4)
730 | - [컴퓨터가 1+1을 하는 과정](https://brunch.co.kr/@lqju/8)
731 | - [컴퓨터의 '보수표현'이란?](https://seollal.tistory.com/700)
732 | - [컴퓨터의 음수 표현과 보수법](https://hs-archive.tistory.com/26)
733 | - [메모리의 구조 (코드, 데이터, 힙, 스택 영역)](https://all-young.tistory.com/17)
734 | - [행위자 모델](https://ko.wikipedia.org/wiki/%ED%96%89%EC%9C%84%EC%9E%90_%EB%AA%A8%EB%8D%B8)
735 |
736 | ## 컴퓨터 비전
737 |
738 | - [OpenCV-특징 검출, 디스크립터, 매칭](https://wjddyd66.github.io/opencv/OpenCV(8)/)
739 |
740 | ## 프론트 엔드
741 |
742 | - [Airbnb의 Server-Driven UI](https://brunch.co.kr/@advisor/37)
743 |
744 | ## 유용한 사이트 정보 블로그 도구 등등
745 |
746 | - [ATLASSIAN 소프트웨어 개발](https://www.atlassian.com/ko/software-development)
747 | - [chatpdf](https://www.chatpdf.com/)
748 | - [civitai](https://civitai.com/) - StableDiffusion Models
749 | - [CodebaseShow](https://codebase.show/) - qualified framework project examples
750 | - [codewars](https://www.codewars.com/) - codekata
751 | - [CSIS](https://www.csis.org/) - Center for Strategic and International Studies
752 | - [DB-Engines](https://db-engines.com/) - DBMS 랭킹
753 | - [Flair.ai](https://flair.ai/) - The AI design tool for product photoshoots
754 | - [fly.io](https://fly.io/) - phoenix 포함 특정 프레임워크 최적화 클라우드 서버
755 | - [GeekNews](https://news.hada.io/) - IT 뉴스 스크랩. (최고)
756 | - [Google Cloud Spanner](https://cloud.google.com/spanner) - Global managing RDB
757 | - [Google 관리 콘솔 도구 상자](https://toolbox.googleapps.com/apps/main/) - DNS 세팅 확인하기 좋음
758 | - [httpstat.us](https://httpstat.us/) - http request로 http protocol 임의로 바꿔서 response 받을 수 있는 사이트
759 | - [infisical](https://infisical.com/) - Open Source SecretOps
760 | - [ipaddress](http://ipaddress.sh/) - IP주소 확인
761 | - [netlify로 사이트 배포하기](https://goddino.tistory.com/190)
762 | - [ngrok](https://ngrok.com/) - 임시로 서버띄워서 확인할때 좋음
763 | - [Patterns for building realtime features](https://zknill.io/posts/patterns-for-building-realtime/)
764 | - [Postgres.app](https://postgresapp.com/)
765 | - [Programming Fonts](https://www.programmingfonts.org/)
766 | - [Quanta Magazine](https://www.quantamagazine.org/)
767 | - [Redhat Topic](https://www.redhat.com/ko/topics)
768 | - [serpapi](https://serpapi.com/) - 검색 엔진 결과 가져오기
769 | - [Simple Icons](https://simpleicons.org/) - 3,000개 이상의 svg 아이콘
770 | - [TechEmpower: Web Framework Benchmarks](https://www.techempower.com/benchmarks/)
771 | - [TIOBE](https://www.tiobe.com/tiobe-index/) - 언어 사용량 랭킹
772 | - [UI Avatars](https://ui-avatars.com/) - 간단하게 글씨로 아바타 placeholder 만들어주는곳
773 | - [VULTR](https://www.vultr.com/products/cloud-compute/) - 저렴한 클라우드 서버
774 | - [가장 효과적인 창업자들을 연구해서 얻은 교훈들](https://news.hada.io/topic?id=6792)
775 | - [아이보스 마케팅 캘린더](https://www.i-boss.co.kr/ab-marketing_calendar)
776 | - [유튜브를 가마우지로 만들어보자](https://this-programmer.tistory.com/509)
777 | - [인디드(indeed)로 살펴본 프로그래밍 언어의 실력대비 연봉 테이블](https://this-programmer.tistory.com/507)
778 | - [Thesify](https://www.thesify.ai/)
779 | - [Elicit](https://elicit.com/)
780 | - [SciSpace](https://bit.ly/)
781 | - [Jenni AI](https://jenni.ai/)
782 | - [Julius AI](https://julius.ai/)
783 | - [AnswerThis](https://answerthis.io)
784 | - [Unriddle](https://www.unriddle.ai/)
785 | - 개발자 블로그
786 | - [Geoffrey Huntley](https://ghuntley.com/)
787 | - [Inpa Dev 👨💻 인파](https://inpa.tistory.com/)
788 | - [N.K LAB](https://blog.neonkid.xyz/)
789 | - [yngie-c](https://yngie-c.github.io/)
790 | - [구르미의 개발 이야기](https://gurumee92.tistory.com/)
791 | - [Hardcore Software by Steven Sinofsky](https://hardcoresoftware.learningbyshipping.com/p/001-becoming-a-microsoftie-chapter)
792 | - 교육
793 | - [K-MOOC](https://www.kmooc.kr/)
794 | - [T academy](https://tacademy.skplanet.com/live/player/listLecture.action)
795 | - 기업 테크 블로그
796 | - [CloudNet@ Blog](https://www.notion.so/gasidaseo/CloudNet-Blog-c9dfa44a27ff431dafdd2edacc8a1863)
797 | - [MADTECH](https://tech.madup.com/)
798 | - [LINE DEV](https://techblog.lycorp.co.jp/ko)
799 | - [SK(주) C&C’s TECH BLOG](https://engineering-skcc.github.io/)
800 | - [SOCAR Tech Blog](https://tech.socarcorp.kr/)
801 | - [syncly](https://www.syncly.app/ko/blog)
802 | - [spoqa 기술 블로그](https://spoqa.github.io/)
803 | - [Tech At Bloomberg](https://www.bloomberg.com/company/stories/category/tech-at-bloomberg/)
804 | - [Dable Tech Blog](https://teamdable.github.io/techblog/)
805 | - [우아한형제들 기술블로그](https://techblog.woowahan.com/)
806 | - [카카오 테크](https://tech.kakao.com/)
807 | - 긱뉴스 스크랩(GeekNews)
808 | - [15년 전의 나에게 해주고 싶은 프로그래밍 조언](https://news.hada.io/topic?id=15848)
809 | - [AI Canon - a16z가 큐레이션한 AI 필수 자료 모음](https://news.hada.io/topic?id=9284)
810 | - [Blink 1.0 릴리즈 - 초경량 x86-64-linux 에뮬레이터](https://news.hada.io/topic?id=9361)
811 | - [Brex의 프롬프트 엔지니어링 가이드](https://news.hada.io/topic?id=9190)
812 | - [CEO를 뽑는 방법 - 비노드 코슬라](https://news.hada.io/topic?id=19271)
813 | - [Figma 데이터베이스 팀이 100배 규모 확장을 견뎌낸 방법](https://news.hada.io/topic?id=13821)
814 | - [Gandalf - 거대 언어 모델이 비밀번호를 유출하게 만드는 게임](https://news.hada.io/topic?id=9160)
815 | - [GitHub Copilot Chat 전체 프롬프트 유출](https://news.hada.io/topic?id=9182)
816 | - [GN⁺: 좋은 소프트웨어 개발 습관](https://news.hada.io/topic?id=17820)
817 | - [Google I/O: Ubiquitous AI가 SEO에 큰 변화를 가져올 것](https://news.hada.io/topic?id=9189)
818 | - [GPS는 망가졌고, 기술 발전을 가로막고 있음. 이제는 GPS 대안 기술을 살펴봐야할 때](https://news.hada.io/topic?id=18638)
819 | - [GPT같은 LLM을 커스텀 데이터셋으로 파인튜닝 하는 방법](https://news.hada.io/topic?id=9288)
820 | - [Notion이 급격한 성장에 맞춰 데이터 레이크를 구축하고 확장한 방법](https://news.hada.io/topic?id=15847)
821 | - [Pinterest가 6명의 엔지니어만으로 1100만명의 사용자로 확장한 방법](https://news.hada.io/topic?id=11825)
822 | - [Prompt Engineering이 진짜 가치가 있는가](https://news.hada.io/topic?id=9285)
823 | - [Same Stop: 애플에서 프로그래머로 26년 일한 뒤의 삶](https://news.hada.io/topic?id=9244)
824 | - [Stuart Ellis의 Python 현대적 모범 사례](https://news.hada.io/topic?id=15837)
825 | - [머신러닝 분야의 임베딩(Embedding)에 대한 상세한 가이드](https://news.hada.io/topic?id=9316)
826 | - [인스타그램이 오직 3명의 엔지니어로 1400만 사용자를 확보한 방법](https://news.hada.io/topic?id=10916)
827 | - [임베딩(Embeddings)은 무엇이고 왜 중요한가](https://news.hada.io/topic?id=11593)
828 | - [향후 5년간 연매출 $25M 이상의 1인 기업이 더 많이 등장할 것](https://news.hada.io/topic?id=9181)
829 | - ["확장되지 않는 일"을 통해 이기는 방법](https://news.hada.io/topic?id=17828)
830 | - 깃허브 프로젝트(GitHub)
831 | - [The Evolution of Trust](https://github.com/ncase/trust)
832 | - 해커뉴스 스크랩(HackerNews)
833 | - [Ask HN: Is it just me or GPT-4's quality has significantly deteriorated lately?](https://news.ycombinator.com/item?id=36134249)
834 | - 기타
835 | - [Double Irish with a Dutch Sandwich](https://namu.wiki/w/%EB%8D%94%EB%B8%94%20%EC%95%84%EC%9D%B4%EB%A6%AC%EC%8B%9C%20%EC%9C%84%EB%93%9C%20%EC%96%B4%20%EB%8D%94%EC%B9%98%20%EC%83%8C%EB%93%9C%EC%9C%84%EC%B9%98)
836 | - [Elo Rating System (엘로 평점 시스템)](https://jeonggyun.tistory.com/126)
837 | - [FreeComputerBooks.com](https://freecomputerbooks.com/)
838 | - [LeadDev 웨스트 코스트 2023의 에반 모리카와 - LeadDev](https://lilys.ai/result?videoId=PeKMEXUrlq4)
839 | - [Mental Models I Find Repeatedly Useful](https://medium.com/@yegg/mental-models-i-find-repeatedly-useful-936f1cc405d)
840 | - [onsites.fyi - bigtech corp interview curation](https://www.onsites.fyi/)
841 | - [TECH ICONS](https://techicons.dev/)
842 | - [Timeline of the xz open source attack](https://research.swtch.com/xz-timeline)
843 | - [xkcd](https://xkcd.com/)
844 | - [Green Software Foundation](https://greensoftware.foundation/)
845 | - [Andy Matuschak](https://andymatuschak.org/)
846 | - [Why, after 6 years, I'm over GraphQL](https://bessey.dev/blog/2024/05/24/why-im-over-graphql/)
847 | - [Unexpected Anti-Patterns for Engineering Leaders — Lessons From Stripe, Uber & Carta](https://review.firstround.com/unexpected-anti-patterns-for-engineering-leaders-lessons-from-stripe-uber-carta/)
848 | - [How to Learn Anything with the Feynman Technique](https://todoist.com/inspiration/feynman-technique)
849 | - [엘로 평점 시스템](https://ko.wikipedia.org/wiki/%EC%97%98%EB%A1%9C_%ED%8F%89%EC%A0%90_%EC%8B%9C%EC%8A%A4%ED%85%9C)
850 | - [파이토치 한국 사용자 모임](https://pytorch.kr/)
851 | - [뭐든 제대로 이해하는 방법](https://www.youtube.com/watch?v=sQYQgiHVyAM)
852 | - [B-Trees](https://www.cs.usfca.edu/~galles/visualization/BTree.html)
853 | - 다른 개발자들의 회고
854 | - [2025년 미국 뉴욕 소프트웨어 엔지니어 취업기](https://www.nyprogrammer.com/p/job-hunting-2025)
855 | - [Why, after 6 years, I'm over GraphQL](https://bessey.dev/blog/2024/05/24/why-im-over-graphql/)
856 | - [Leaving Rust gamedev after 3 years](https://loglog.games/blog/leaving-rust-gamedev/)
857 | - [I've Built My First Successful Side Project, and I Hate It](https://switowski.com/blog/i-have-built-my-first-successful-side-project-and-i-hate-it/)
858 |
--------------------------------------------------------------------------------